1
package opencog.spacetime.tutorial.app;
3
import static opencog.spacetime.shader.CommonAttributes.LINE_SHADER;
4
import static opencog.spacetime.shader.CommonAttributes.POLYGON_SHADER;
5
import static opencog.spacetime.shader.CommonAttributes.SMOOTH_SHADING;
9
import javax.swing.SwingConstants;
11
import opencog.math.MatrixBuilder;
12
import opencog.spacetime.geometry.BallAndStickFactory;
13
import opencog.spacetime.geometry.IndexedLineSetFactory;
14
import opencog.spacetime.geometry.PointSetFactory;
15
import opencog.spacetime.shader.DefaultGeometryShader;
16
import opencog.spacetime.shader.DefaultLineShader;
17
import opencog.spacetime.shader.DefaultPointShader;
18
import opencog.spacetime.shader.DefaultPolygonShader;
19
import opencog.spacetime.shader.DefaultTextShader;
20
import opencog.spacetime.shader.RenderingHintsShader;
21
import opencog.spacetime.shader.ShaderUtility;
22
import opencog.spacetime.space.Appearance;
23
import opencog.spacetime.space.IndexedLineSet;
24
import opencog.spacetime.space.SpaceComponent;
25
import opencog.spacetime.space.data.Attribute;
26
import opencog.spacetime.swing.JRViewer;
27
import opencog.spacetime.util.SceneGraphUtility;
32
* without tubes (bresenham)
34
* 2. with stippling (JOGL backend only)
36
* edges: list of line segments
37
* 3. color from appearance, opaque
38
* 4. color from appearance, transparency enabled
39
* 5. color from vertices of line set
40
* 6. with relative radii allowing varying thickness
41
* edges: a single long "edge"
42
* 7. color from vertices of line set
43
* 8. with relative radii, and a custom "cross section" curve
46
* 1. Textures cannot be applied to these tubes.
47
* See {@link BallAndStickFactory} for a class which allows this.
48
* 2. Width of lines (Examples 1 and 2) and tubes (the rest) are set independently
49
* since linewidth is specified in pixels, and tube radius in object coordinates.
50
* 3. Note that the indexed line sets demonstrate different ways to specify the edges
52
* a. as many line segments, or
53
* b. as a single long curve
54
* See the method {@link IndexedLineSetFactory#setEdgeIndices()}.
55
* The resulting tubes will appear differently.
56
* 4. Colors specified in the shader are ALWAYS RGB values; alpha (transparency) values
57
* must be set using the separate "transparency" attribute.
58
* 5. This example has been tested on the JOGL backend; other backends may not yield the
59
* same behavior, particularly where rendering hints are involved.
63
public class LineShaderExample {
65
public static void main(String[] args) {
67
// data needed for the various versions of the line set created here
68
double[][] verts = new double[numPoints][],
69
edgeColors = new double[numPoints][];
70
double[] relrad = new double[numPoints];
71
int[][] edges = new int[numPoints][2],
72
singleEdge = new int[1][numPoints+1];
73
// create a ring and associated data
74
for (int i=0; i<numPoints; ++i) {
75
double angle = (Math.PI*2*i)/numPoints;
76
verts[i] = new double[]{Math.cos(angle), Math.sin(angle), 0};
77
edgeColors[i] = new double[]{verts[i][0]*.5+.5, verts[i][1]*.5+.5,0.0};
78
relrad[i] = verts[i][0]+1.5;
80
edges[i][1] = (i+1)%numPoints;
83
singleEdge[0][numPoints] = 0;
85
// each sample gets a numeric label at its geometric center point. Prepare the appearance.
86
Appearance labelAp = new Appearance();
87
DefaultGeometryShader dgs = ShaderUtility.createDefaultGeometryShader(labelAp, false);
88
dgs.setShowPoints(true);
89
DefaultPointShader pointShader = (DefaultPointShader)dgs.getPointShader();
90
pointShader.setPointRadius(.0001);
91
DefaultTextShader pts = (DefaultTextShader) (pointShader).getTextShader();
93
pts.setOffset(new double[]{0,0,0});
94
pts.setAlignment(SwingConstants.CENTER);
96
SpaceComponent world = SceneGraphUtility.createFullSceneGraphComponent("world");
97
world.getAppearance().setAttribute(LINE_SHADER+"."+POLYGON_SHADER+"."+SMOOTH_SHADING, true);
98
world.getAppearance().setAttribute(POLYGON_SHADER+"."+SMOOTH_SHADING, false);
100
for (int i = 0; i<numSamples; ++i) {
101
SpaceComponent child = SceneGraphUtility.createFullSceneGraphComponent("child"+i);
102
world.addChild(child);
103
// create the label at the center of the example
104
SpaceComponent label = SceneGraphUtility.createFullSceneGraphComponent("label"+i);
105
PointSetFactory labelFac = new PointSetFactory();
106
labelFac.setVertexCount(1);
107
labelFac.setVertexCoordinates(new double[]{0,0,0});
108
labelFac.setVertexLabels(new String[]{""+(i+1)});
110
label.setGeometry(labelFac.getPointSet());
111
label.setAppearance(labelAp);
112
child.addChild(label);
114
// set up the indexed line set for this example
115
IndexedLineSetFactory lsf = new IndexedLineSetFactory();
116
lsf.setVertexCount(numPoints);
117
lsf.setVertexCoordinates(verts);
118
if (i == 1) lsf.setVertexNormals(verts); // outward pointing normals for lighting enabled
119
lsf.setEdgeCount(numPoints);
120
lsf.setEdgeIndices(edges);
121
lsf.setVertexColors(edgeColors);
123
if (i == 4 || i == 5) {
124
lsf.setEdgeColors(edgeColors);
126
lsf.setEdgeAttribute(Attribute.RELATIVE_RADII, relrad);
129
// make a line set with vertex colors and a single long edge
130
// and show how to use the RELATIVE_RADII attribute to modulate size of tube
131
else if (i == 6 || i == 7) {
133
lsf.setEdgeIndices(singleEdge);
135
lsf.setVertexAttribute(Attribute.RELATIVE_RADII, relrad);
139
IndexedLineSet ils = lsf.getIndexedLineSet();
140
child.setGeometry(ils);
142
// set up the line shader
143
Appearance ap = child.getAppearance();
144
dgs = ShaderUtility.createDefaultGeometryShader(ap, true);
145
dgs.setShowPoints(false);
146
dgs.setShowLines(true);
147
RenderingHintsShader rhs = ShaderUtility.createDefaultRenderingHintsShader(ap, true);
148
DefaultLineShader dls = (DefaultLineShader) dgs.createLineShader("default");
149
// this polygon shader controls how the tubes are rendered
150
DefaultPolygonShader dpls = (DefaultPolygonShader) dls.createPolygonShader("default");
151
MatrixBuilder.euclidean().translate(0,0,-i*.5).assignTo(child);
153
case 0: // default rendering with bresenham lines
154
case 1: // bresenham again, but with "stippling" (dots and dashes) -JOGL only
155
dls.setTubeDraw(false);
156
dls.setLineWidth(2.0);
157
if (i == 1) { // activate stippling and lighting
158
dls.setDiffuseColor(Color.red);
159
dls.setLineLighting(true);
160
dls.setLineStipple(true);
161
dls.setLineStipplePattern(0xf0f0);
162
dls.setLineFactor(2); // scales the dots and dashes
165
case 2: // ordinary opaque tubes
166
case 3: // transparency activated for the tubes coming from appearances. like these
167
case 4: // opaque tubes with edge colors
168
case 5: // opaque tubes with vertex colors and relative radii
169
case 6: // opaque tubes with vertex colors and a single, long edge
170
case 7: // same as 6 with a non-default cross section
171
dls.setTubeDraw(true); // the default
172
dls.setTubeRadius(.05);
173
if (i==7) ap.setAttribute("crossSection", verts);
174
dpls.setTransparency(.6);
175
dpls.setDiffuseColor(Color.cyan);
176
rhs.setTransparencyEnabled(true);
177
rhs.setOpaqueTubesAndSpheres(i != 3);
178
if (i == 5 || i == 6 || i == 7) { // use vertex colors
179
dls.setVertexColors(true);
181
if (i == 6) dpls.setSmoothShading(false);
186
JRViewer.display(world);