//
// VisADIndexedTriangleStripArray.java
//
/*
VisAD system for interactive analysis and visualization of numerical
data. Copyright (C) 1996 - 2017 Bill Hibbard, Curtis Rueden, Tom
Rink, Dave Glowacki, Steve Emmerson, Tom Whittaker, Don Murray, and
Tommy Jasmin.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package visad;
/**
VisADIndexedTriangleStripArray stands in for
j3d.IndexedTriangleStripArray and is Serializable.
*/
public class VisADIndexedTriangleStripArray extends VisADGeometryArray {
public int indexCount; // should = indices.length
public int[] indices;
public int[] stripVertexCounts;
public static VisADIndexedTriangleStripArray
merge(VisADIndexedTriangleStripArray[] arrays)
throws VisADException {
if (arrays == null || arrays.length == 0) return null;
VisADIndexedTriangleStripArray array =
new VisADIndexedTriangleStripArray();
merge(arrays, array);
int count = 0;
int nind = 0;
int nstrips = 0;
int n = arrays.length;
// WLH 1 May 99
int[] start = new int[n];
start[0] = 0;
for (int i=0; i 0) start[i] = start[i-1] + arrays[i-1].vertexCount;
}
}
if (nstrips <= 0) return null;
int[] indices = new int[nind];
int[] stripVertexCounts = new int[nstrips];
nind = 0;
nstrips = 0;
for (int i=0; i= 3) {
svcs[svc_index] = accum;
svc_index++;
}
last = indices[i+1];
accum = 1; // reset strip counter;
continue;
}
// lon_axis >= 0
// split line by interpolation
float a, b;
float coord_first, coord_second;
if (lons[indices[i]] < low) {
a = lons[indices[i]] - bottom;
b = top - lons[indices[i+1]];
coord_first = coord_bottom;
coord_second = coord_top;
}
else {
a = top - lons[indices[i]];
b = lons[indices[i+1]] - bottom;
coord_first = coord_top;
coord_second = coord_bottom;
}
float alpha = b / (a + b);
alpha = (alpha != alpha || alpha < 0.0f) ? 0.0f :
((1.0f < alpha) ? 1.0f : alpha);
float beta = 1.0f - alpha;
mid_first = coord_index++;
mid_second = coord_index++;
int f3 = 3 * mid_first;
int s3 = 3 * mid_second;
int i3 = 3 * indices[i];
int ip3 = 3 * indices[i+1];
coords[f3] = alpha * coordinates[i3] + beta * coordinates[ip3];
coords[f3+1] = alpha * coordinates[i3+1] + beta * coordinates[ip3+1];
coords[f3+2] = alpha * coordinates[i3+2] + beta * coordinates[ip3+2];
coords[s3] = coords[f3];
coords[s3+1] = coords[f3+1];
coords[s3+2] = coords[f3+2];
coords[f3+lon_axis] = coord_first;
coords[s3+lon_axis] = coord_second;
if (normals != null) {
nos[f3] = alpha * normals[i3] + beta * normals[ip3];
nos[f3+1] = alpha * normals[i3+1] + beta * normals[ip3+1];
nos[f3+2] = alpha * normals[i3+2] + beta * normals[ip3+2];
nos[s3] = nos[f3];
nos[s3+1] = nos[f3+1];
nos[s3+2] = nos[f3+2];
}
if (color_length == 3) {
cols[f3] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[i3]) +
beta * ShadowType.byteToFloat(colors[ip3]));
cols[f3+1] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[i3+1]) +
beta * ShadowType.byteToFloat(colors[ip3+1]));
cols[f3+2] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[i3+2]) +
beta * ShadowType.byteToFloat(colors[ip3+2]));
cols[s3] = cols[f3];
cols[s3+1] = cols[f3+1];
cols[s3+2] = cols[f3+2];
}
else if (color_length == 4) {
int f4 = 4 * mid_first;
int s4 = 4 * mid_second;
int i4 = 4 * indices[i];
int ip4 = 4 * indices[i+1];
cols[f4] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[i4]) +
beta * ShadowType.byteToFloat(colors[ip4]));
cols[f4+1] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[i4+1]) +
beta * ShadowType.byteToFloat(colors[ip4+1]));
cols[f4+2] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[i4+2]) +
beta * ShadowType.byteToFloat(colors[ip4+2]));
cols[f4+3] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[i4+3]) +
beta * ShadowType.byteToFloat(colors[ip4+3]));
cols[s4] = cols[f4];
cols[s4+1] = cols[f4+1];
cols[s4+2] = cols[f4+2];
cols[s4+3] = cols[f4+3];
}
if (texCoords != null) {
int f2 = 2 * mid_first;
int s2 = 2 * mid_second;
int i2 = 2 * indices[i];
int ip2 = 2 * indices[i+1];
texs[f2] = alpha * texCoords[i2] + beta * texCoords[ip2];
texs[f2+1] = alpha * texCoords[i2+1] + beta * texCoords[ip2+1];
texs[s2] = cols[f2];
texs[s2+1] = cols[f2+1];
}
}
else { // no split
this_split = false;
}
if (accum > 0 && this_split != last_split && lon_axis >= 0) {
// need to compute mid edge from -3 to +3
// split line by interpolation
float a, b;
float coord_first, coord_second;
if (lons[indices[i-1]] < low) {
a = lons[indices[i-1]] - bottom;
b = top - lons[indices[i+1]];
coord_first = coord_bottom;
coord_second = coord_top;
}
else {
a = top - lons[indices[i-1]];
b = lons[indices[i+1]] - bottom;
coord_first = coord_top;
coord_second = coord_bottom;
}
float alpha = b / (a + b);
alpha = (alpha != alpha || alpha < 0.0f) ? 0.0f :
((1.0f < alpha) ? 1.0f : alpha);
float beta = 1.0f - alpha;
sillymid_first = coord_index++;
sillymid_second = coord_index++;
int f3 = 3 * sillymid_first;
int s3 = 3 * sillymid_second;
int im3 = 3 * indices[i-1];
int ip3 = 3 * indices[i+1];
coords[f3] = alpha * coordinates[im3] + beta * coordinates[ip3];
coords[f3+1] = alpha * coordinates[im3+1] + beta * coordinates[ip3+1];
coords[f3+2] = alpha * coordinates[im3+2] + beta * coordinates[ip3+2];
coords[s3] = coords[f3];
coords[s3+1] = coords[f3+1];
coords[s3+2] = coords[f3+2];
coords[f3+lon_axis] = coord_first;
coords[s3+lon_axis] = coord_second;
if (normals != null) {
nos[f3] = alpha * normals[im3] + beta * normals[ip3];
nos[f3+1] = alpha * normals[im3+1] + beta * normals[ip3+1];
nos[f3+2] = alpha * normals[im3+2] + beta * normals[ip3+2];
nos[s3] = nos[f3];
nos[s3+1] = nos[f3+1];
nos[s3+2] = nos[f3+2];
}
if (color_length == 3) {
cols[f3] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[im3]) +
beta * ShadowType.byteToFloat(colors[ip3]));
cols[f3+1] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[im3+1]) +
beta * ShadowType.byteToFloat(colors[ip3+1]));
cols[f3+2] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[im3+2]) +
beta * ShadowType.byteToFloat(colors[ip3+2]));
cols[s3] = cols[f3];
cols[s3+1] = cols[f3+1];
cols[s3+2] = cols[f3+2];
}
else if (color_length == 4) {
int f4 = 4 * mid_first;
int s4 = 4 * mid_second;
int im4 = 4 * indices[i-1];
int ip4 = 4 * indices[i+1];
cols[f4] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[im4]) +
beta * ShadowType.byteToFloat(colors[ip4]));
cols[f4+1] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[im4+1]) +
beta * ShadowType.byteToFloat(colors[ip4+1]));
cols[f4+2] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[im4+2]) +
beta * ShadowType.byteToFloat(colors[ip4+2]));
cols[f4+3] = ShadowType.floatToByte(
alpha * ShadowType.byteToFloat(colors[im4+3]) +
beta * ShadowType.byteToFloat(colors[ip4+3]));
cols[s4] = cols[f4];
cols[s4+1] = cols[f4+1];
cols[s4+2] = cols[f4+2];
cols[s4+3] = cols[f4+3];
}
if (texCoords != null) {
int f2 = 2 * mid_first;
int s2 = 2 * mid_second;
int im2 = 2 * indices[i-1];
int ip2 = 2 * indices[i+1];
texs[f2] = alpha * texCoords[im2] + beta * texCoords[ip2];
texs[f2+1] = alpha * texCoords[im2+1] + beta * texCoords[ip2+1];
texs[s2] = cols[f2];
texs[s2+1] = cols[f2+1];
}
}
if (this_split) {
if (accum == 0) {
early = mid_second;
last = indices[i+1];
accum = 2;
continue; // don't make any triangles yet, for accum = 0
} // end if (accum == 0)
else if (last_split) { // && this_split
point = mid_first;
accum++;
if (accum == 3) {
inds[ind_index++] = early;
inds[ind_index++] = last;
inds[ind_index++] = point;
}
else {
inds[ind_index++] = point;
}
// bind off
svcs[svc_index] = accum;
svc_index++;
// accum = 0, but more to come
// create a 2-triangle strip
// (last_mid_first, i-3, mid_second, i+3)
early = last_mid_first;
last = indices[i-1];
point = mid_second;
accum = 3;
inds[ind_index++] = early;
inds[ind_index++] = last;
inds[ind_index++] = point;
point = indices[i+1];
accum++;
inds[ind_index++] = point;
}
else { // !last_split && accum > 0 && this_split
// add (mid_first, i-3, sillymid_first)
point = mid_first;
accum++;
if (accum == 2) {
early = last;
last = point;
}
else if (accum == 3) {
inds[ind_index++] = early;
inds[ind_index++] = last;
inds[ind_index++] = point;
}
else {
inds[ind_index++] = point;
}
point = indices[i-1];
accum++;
if (accum == 2) {
early = last;
last = point;
}
else if (accum == 3) {
inds[ind_index++] = early;
inds[ind_index++] = last;
inds[ind_index++] = point;
}
else {
inds[ind_index++] = point;
}
point = sillymid_first;
accum++;
if (accum == 2) {
early = last;
last = point;
}
else if (accum == 3) {
inds[ind_index++] = early;
inds[ind_index++] = last;
inds[ind_index++] = point;
}
else {
inds[ind_index++] = point;
}
// (accum >= 3)
svcs[svc_index] = accum;
svc_index++;
// accum = 0, but more to come
// start a triangle strip
// (sillymid_second, mid_second, i+3)
early = sillymid_second;
last = mid_second;
point = indices[i+1];
accum = 3;
inds[ind_index++] = early;
inds[ind_index++] = last;
inds[ind_index++] = point;
}
}
else { // !this_split
if (accum == 0) {
early = indices[i];
last = indices[i+1];
accum = 2;
continue; // don't make any triangles yet, for accum = 0
} // end if (accum == 0)
else if (last_split && lon_axis >= 0) { // && !this_split
// first, bind off
if (accum >= 3) {
svcs[svc_index] = accum;
svc_index++;
}
// accum = 0, but more to come
early = indices[i-1];
last = last_mid_first;
point = sillymid_first;
accum = 3;
inds[ind_index++] = early;
inds[ind_index++] = last;
inds[ind_index++] = point;
// bind off again
svcs[svc_index] = accum;
svc_index++;
// accum = 0, but more to come
// create a 2-triangle strip
// (last_mid_second, sillymid_second, i, i+3)
early = last_mid_second;
last = sillymid_second;
point = indices[i];
accum = 3;
inds[ind_index++] = early;
inds[ind_index++] = last;
inds[ind_index++] = point;
point = indices[i+1];
accum++;
inds[ind_index++] = point;
}
else { // (!last_split || lon_axis < 0) && accum > 0 && !this_split
// just add the next point (i+3)
point = indices[i+1];
accum++;
if (accum == 2) {
early = last;
last = point;
}
else if (accum == 3) {
inds[ind_index++] = early;
inds[ind_index++] = last;
inds[ind_index++] = point;
}
else {
inds[ind_index++] = point;
}
}
} // end if no split
} // end for (int i=last_i; i= 3) {
svcs[svc_index] = accum;
svc_index++;
}
last_i += stripVertexCounts[i_svc];
} // end for (int i_svc=0; i_svc= 0) {
accum++;
if (accum >= 3) {
int iml = i;
if (accum == 3) {
iml = i - 2;
}
for (int im=iml; im<=i; im++) {
new_indices[m] = compress[indices[im]];
m++;
} // end for (im=iml; im<=i; im+=3)
} // end if (accum >= 3)
}
else { // missing coordinates values
any_missing = true;
if (accum >= 3) {
svcs[svc_index] = accum;
svc_index++;
}
accum = 0; // reset strip counter;
}
} // end for (int i=last_i; i= 3) {
svcs[svc_index] = accum;
svc_index++;
}
last_i += stripVertexCounts[i_svc];
} // end for (int i_svc=0; i_svc
Ads help maintain this website.