1 /*
2  * $RCSfile: ShaderAppearance.java,v $
3  *
4  * Copyright 2004-2008 Sun Microsystems, Inc.  All Rights Reserved.
5  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
6  *
7  * This code is free software; you can redistribute it and/or modify it
8  * under the terms of the GNU General Public License version 2 only, as
9  * published by the Free Software Foundation.  Sun designates this
10  * particular file as subject to the "Classpath" exception as provided
11  * by Sun in the LICENSE file that accompanied this code.
12  *
13  * This code is distributed in the hope that it will be useful, but WITHOUT
14  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
15  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
16  * version 2 for more details (a copy is included in the LICENSE file that
17  * accompanied this code).
18  *
19  * You should have received a copy of the GNU General Public License version
20  * 2 along with this work; if not, write to the Free Software Foundation,
21  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
22  *
23  * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
24  * CA 95054 USA or visit www.sun.com if you need additional information or
25  * have any questions.
26  *
27  * $Revision: 1.5 $
28  * $Date: 2008/02/28 20:17:29 $
29  * $State: Exp $
30  */
31 
32 package javax.media.j3d;
33 
34 import java.util.Hashtable;
35 
36 /**
37  * <p>The ShaderAppearance object defines programmable shading attributes
38  * that can be set as a component object of a Shape3D node. The
39  * ShaderAppearance rendering state adds the following attributes in
40  * addition to those defined by Appearance:</p>
41  *
42  * <ul>
43  * <li>Shader program - specifies the shader program...</li>
44  *
45  * <p></p>
46  * <li>Shader attribute set - specifies the shader parameters, both as
47  * explicit attributes and as implicit bindings to Java 3D
48  * state...</li>
49  * </ul>
50  *
51  * <p>The ShaderAppearance object modifies the definition of some of the
52  * attributes in Appearance:</p>
53  *
54  * <ul>
55  * <li>Coloring attributes - XXXXX</li>
56  *
57  * <p></p>
58  * <li>Line attributes - XXXXX</li>
59  *
60  * <p></p>
61  * <li>Point attributes - XXXXX</li>
62  *
63  * <p></p>
64  * <li>Polygon attributes - XXXXX</li>
65  *
66  * <p></p>
67  * <li>Rendering attributes - XXXXX</li>
68  *
69  * <p></p>
70  * <li>Transparency attributes - XXXXX</li>
71  *
72  * <p></p>
73  * <li>Material - XXXXX</li>
74  *
75  * <p></p>
76  * <li>Texture - XXXXX</li>
77  *
78  * <p></p>
79  * <li>Texture attributes - XXXXX</li>
80  *
81  * <p></p>
82  * <li>Texture coordinate generation - XXXXX</li>
83  *
84  * <p></p>
85  * <li>Texture unit state - XXXXX</li>
86  * </ul>
87  *
88  * @see ShaderProgram
89  * @see ShaderAttributeSet
90  *
91  * @since Java 3D 1.4
92  */
93 public class ShaderAppearance extends Appearance {
94     /**
95      * Specifies that this ShaderAppearance object allows reading its
96      * ShaderProgram component information.
97      */
98     public static final int
99 	ALLOW_SHADER_PROGRAM_READ =
100 	CapabilityBits.SHADER_APPEARANCE_ALLOW_SHADER_PROGRAM_READ;
101 
102     /**
103      * Specifies that this ShaderAppearance object allows writing its
104      * ShaderProgram component information.
105      */
106     public static final int
107 	ALLOW_SHADER_PROGRAM_WRITE =
108 	CapabilityBits.SHADER_APPEARANCE_ALLOW_SHADER_PROGRAM_WRITE;
109 
110     /**
111      * Specifies that this ShaderAppearance object allows reading its
112      * ShaderAttributeSet component information.
113      */
114     public static final int
115 	ALLOW_SHADER_ATTRIBUTE_SET_READ =
116 	CapabilityBits.SHADER_APPEARANCE_ALLOW_SHADER_ATTRIBUTE_SET_READ;
117 
118     /**
119      * Specifies that this ShaderAppearance object allows writing its
120      * ShaderAttributeSet component information.
121      */
122     public static final int
123 	ALLOW_SHADER_ATTRIBUTE_SET_WRITE =
124 	CapabilityBits.SHADER_APPEARANCE_ALLOW_SHADER_ATTRIBUTE_SET_WRITE;
125 
126    // Array for setting default read capabilities
127     private static final int[] readCapabilities = {
128 	ALLOW_SHADER_PROGRAM_READ,
129 	ALLOW_SHADER_ATTRIBUTE_SET_READ
130     };
131 
132     /**
133      * Constructs a ShaderAppearance component object using defaults for all
134      * state variables. All component object references are initialized
135      * to null.
136      */
ShaderAppearance()137     public ShaderAppearance() {
138 	// Just use default values
139         // set default read capabilities
140         setDefaultReadCapabilities(readCapabilities);
141     }
142 
143     /**
144      * Creates the retained mode ShaderAppearanceRetained object that this
145      * ShaderAppearance component object will point to.
146      */
createRetained()147     void createRetained() {
148 	this.retained = new ShaderAppearanceRetained();
149 	this.retained.setSource(this);
150     }
151 
152     /**
153      * Sets the ShaderProgram object to the specified object.  Setting it to
154      * null causes a default pass-through shader to be used ???
155      *
156      * @param shaderProgram object that specifies the desired shader program
157      * @exception CapabilityNotSetException if appropriate capability is
158      * not set and this object is part of live or compiled scene graph
159      */
setShaderProgram(ShaderProgram shaderProgram)160     public void setShaderProgram(ShaderProgram shaderProgram) {
161 
162         if (isLiveOrCompiled()) {
163 	  if(!this.getCapability(ALLOW_SHADER_PROGRAM_WRITE))
164 	    throw new CapabilityNotSetException(J3dI18N.getString("ShaderAppearance0"));
165 	}
166 
167 	((ShaderAppearanceRetained)this.retained).setShaderProgram(shaderProgram);
168 
169     }
170 
171 
172     /**
173      * Retrieves the current ShaderProgram object.
174      *
175      * @return the ShaderProgram object
176      * @exception CapabilityNotSetException if appropriate capability is
177      * not set and this object is part of live or compiled scene graph
178      */
getShaderProgram()179     public ShaderProgram getShaderProgram() {
180 
181         if (isLiveOrCompiled()) {
182 	    if(!this.getCapability(ALLOW_SHADER_PROGRAM_READ))
183 		throw new CapabilityNotSetException(J3dI18N.getString("ShaderAppearance1"));
184 	}
185 	return ((ShaderAppearanceRetained)this.retained).getShaderProgram();
186     }
187 
188 
189     /**
190      * Sets the ShaderAttributeSet object to the specified object.  Setting it to
191      * null is equivalent to specifying an empty set of attributes.
192      *
193      * @param shaderAttributeSet object that specifies the desired shader attributes
194      * @exception CapabilityNotSetException if appropriate capability is
195      * not set and this object is part of live or compiled scene graph
196      */
setShaderAttributeSet(ShaderAttributeSet shaderAttributeSet)197     public void setShaderAttributeSet(ShaderAttributeSet shaderAttributeSet) {
198         if (isLiveOrCompiled()) {
199 	    if(!this.getCapability(ALLOW_SHADER_ATTRIBUTE_SET_WRITE))
200 		throw new CapabilityNotSetException(J3dI18N.getString("ShaderAppearance2"));
201 	}
202 
203 	((ShaderAppearanceRetained)this.retained).setShaderAttributeSet(shaderAttributeSet);
204     }
205 
206 
207     /**
208      * Retrieves the current ShaderAttributeSet object.
209      *
210      * @return the ShaderAttributeSet object
211      * @exception CapabilityNotSetException if appropriate capability is
212      * not set and this object is part of live or compiled scene graph
213      */
getShaderAttributeSet()214     public ShaderAttributeSet getShaderAttributeSet() {
215         if (isLiveOrCompiled()) {
216 	    if(!this.getCapability(ALLOW_SHADER_ATTRIBUTE_SET_READ))
217 		throw new CapabilityNotSetException(J3dI18N.getString("ShaderAppearance3"));
218 	}
219 	return ((ShaderAppearanceRetained)this.retained).getShaderAttributeSet();
220     }
221 
222 
223    /**
224      * @deprecated replaced with cloneNodeComponent(boolean forceDuplicate)
225      */
cloneNodeComponent()226     public NodeComponent cloneNodeComponent() {
227         ShaderAppearance a = new ShaderAppearance();
228         a.duplicateNodeComponent(this);
229         return a;
230     }
231 
232     /**
233      * NOTE: Applications should <i>not</i> call this method directly.
234      * It should only be called by the cloneNode method.
235      *
236      * @deprecated replaced with duplicateNodeComponent(
237      *  NodeComponent originalNodeComponent, boolean forceDuplicate)
238      */
duplicateNodeComponent(NodeComponent originalNodeComponent)239     public void duplicateNodeComponent(NodeComponent originalNodeComponent) {
240 	checkDuplicateNodeComponent(originalNodeComponent);
241     }
242 
243    /**
244      * Copies all ShaderAppearance information from
245      * <code>originalNodeComponent</code> into
246      * the current node.  This method is called from the
247      * <code>cloneNode</code> method which is, in turn, called by the
248      * <code>cloneTree</code> method.<P>
249      *
250      * @param originalNodeComponent the original node to duplicate.
251      * @param forceDuplicate when set to <code>true</code>, causes the
252      *  <code>duplicateOnCloneTree</code> flag to be ignored.  When
253      *  <code>false</code>, the value of each node's
254      *  <code>duplicateOnCloneTree</code> variable determines whether
255      *  NodeComponent data is duplicated or copied.
256      *
257      * @exception RestrictedAccessException if this object is part of a live
258      *  or compiled scenegraph.
259      *
260      * @see Node#cloneTree
261      * @see NodeComponent#setDuplicateOnCloneTree
262      */
duplicateAttributes(NodeComponent originalNodeComponent, boolean forceDuplicate)263     void duplicateAttributes(NodeComponent originalNodeComponent,
264 			     boolean forceDuplicate) {
265 	super.duplicateAttributes(originalNodeComponent, forceDuplicate);
266 
267 	Hashtable hashtable = originalNodeComponent.nodeHashtable;
268 
269 	ShaderAppearanceRetained app =
270 	    (ShaderAppearanceRetained) originalNodeComponent.retained;
271 
272 	ShaderAppearanceRetained rt = (ShaderAppearanceRetained) retained;
273 
274 	rt.setShaderProgram((ShaderProgram) getNodeComponent(app.getShaderProgram(),
275 				forceDuplicate,
276 				hashtable));
277     }
278 
279     /**
280      *  This function is called from getNodeComponent() to see if any of
281      *  the sub-NodeComponents  duplicateOnCloneTree flag is true.
282      *  If it is the case, current NodeComponent needs to
283      *  duplicate also even though current duplicateOnCloneTree flag is false.
284      *  This should be overwrite by NodeComponent which contains sub-NodeComponent.
285      */
duplicateChild()286     boolean duplicateChild() {
287 	if (super.duplicateChild())
288 	    return true;
289 
290 	if (getDuplicateOnCloneTree())
291 	    return true;
292 
293 	ShaderAppearanceRetained rt = (ShaderAppearanceRetained) retained;
294 
295 	NodeComponent nc;
296 
297 	nc = rt.getShaderProgram();
298 	if ((nc != null) && nc.getDuplicateOnCloneTree())
299 	    return true;
300 
301 	return false;
302     }
303 
304 }
305