Project

General

Profile

Download (27.2 KB) Statistics
| Branch: | Revision:

library / src / main / java / org / distorted / library / mesh / MeshBase.java @ 2aeb75aa

1 d333eb6b Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
2
// Copyright 2016 Leszek Koltunski                                                               //
3
//                                                                                               //
4 46b572b5 Leszek Koltunski
// This file is part of Distorted.                                                               //
5 d333eb6b Leszek Koltunski
//                                                                                               //
6 46b572b5 Leszek Koltunski
// Distorted is free software: you can redistribute it and/or modify                             //
7 d333eb6b Leszek Koltunski
// it under the terms of the GNU General Public License as published by                          //
8
// the Free Software Foundation, either version 2 of the License, or                             //
9
// (at your option) any later version.                                                           //
10
//                                                                                               //
11 46b572b5 Leszek Koltunski
// Distorted is distributed in the hope that it will be useful,                                  //
12 d333eb6b Leszek Koltunski
// but WITHOUT ANY WARRANTY; without even the implied warranty of                                //
13
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the                                 //
14
// GNU General Public License for more details.                                                  //
15
//                                                                                               //
16
// You should have received a copy of the GNU General Public License                             //
17 46b572b5 Leszek Koltunski
// along with Distorted.  If not, see <http://www.gnu.org/licenses/>.                            //
18 d333eb6b Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
19
20 6c00149d Leszek Koltunski
package org.distorted.library.mesh;
21 6a06a912 Leszek Koltunski
22 b7074bc6 Leszek Koltunski
import android.opengl.GLES30;
23 f046b159 Leszek Koltunski
import android.util.Log;
24 6c00149d Leszek Koltunski
25 f046b159 Leszek Koltunski
import org.distorted.library.effect.VertexEffect;
26 36d65d88 Leszek Koltunski
import org.distorted.library.effectqueue.EffectQueue;
27 7602a827 Leszek Koltunski
import org.distorted.library.main.InternalBuffer;
28 da681e7e Leszek Koltunski
import org.distorted.library.program.DistortedProgram;
29 a3a05347 Leszek Koltunski
import org.distorted.library.type.Static4D;
30 6c00149d Leszek Koltunski
31 f046b159 Leszek Koltunski
import java.nio.ByteBuffer;
32
import java.nio.ByteOrder;
33
import java.nio.FloatBuffer;
34 c90aca24 Leszek Koltunski
import java.util.ArrayList;
35 6a06a912 Leszek Koltunski
36
///////////////////////////////////////////////////////////////////////////////////////////////////
37 e0b6c593 Leszek Koltunski
/**
38 e5ba319d Leszek Koltunski
 * Abstract class which represents a Mesh, ie an array of vertices (rendered as a TRIANGLE_STRIP).
39 e0b6c593 Leszek Koltunski
 * <p>
40 da681e7e Leszek Koltunski
 * If you want to render to a particular shape, extend from here, construct a float array
41 7a5e538a Leszek Koltunski
 * containing per-vertex attributes, and call back setAttribs().
42 e0b6c593 Leszek Koltunski
 */
43 715e7726 Leszek Koltunski
public abstract class MeshBase
44 6a06a912 Leszek Koltunski
   {
45 36d65d88 Leszek Koltunski
   private static final int MAX_COMPONENTS= 100;
46 07206c71 Leszek Koltunski
   private static final int DEFAULT_ASSOCIATION = 0xffffffff;
47 bc208a9c Leszek Koltunski
48 227b9bca Leszek Koltunski
   // sizes of attributes of an individual vertex.
49
   private static final int POS_DATA_SIZE= 3; // vertex coordinates: x,y,z
50
   private static final int NOR_DATA_SIZE= 3; // normal vector: x,y,z
51
   private static final int INF_DATA_SIZE= 3; // 'inflate' vector: x,y,z
52 7a5e538a Leszek Koltunski
   private static final int TEX_DATA_SIZE= 2; // texture coordinates: s,t
53 36d65d88 Leszek Koltunski
   private static final int COM_DATA_SIZE= 1; // component number, a single float
54 6f2d931d Leszek Koltunski
55
   static final int POS_ATTRIB   = 0;
56
   static final int NOR_ATTRIB   = POS_DATA_SIZE;
57
   static final int INF_ATTRIB   = POS_DATA_SIZE + NOR_DATA_SIZE;
58 e54bfada Leszek Koltunski
   static final int TEX_ATTRIB   = 0;
59 36d65d88 Leszek Koltunski
   static final int COM_ATTRIB   = TEX_DATA_SIZE;
60 bc208a9c Leszek Koltunski
61 e54bfada Leszek Koltunski
   static final int VERT1_ATTRIBS= POS_DATA_SIZE + NOR_DATA_SIZE + INF_DATA_SIZE;  // number of attributes of a vertex (the part changed by preapply)
62 36d65d88 Leszek Koltunski
   static final int VERT2_ATTRIBS= TEX_DATA_SIZE + COM_DATA_SIZE;                  // number of attributes of a vertex (the 'preapply invariant' part)
63 e54bfada Leszek Koltunski
   static final int TRAN_ATTRIBS = POS_DATA_SIZE + NOR_DATA_SIZE + INF_DATA_SIZE;  // number of attributes of a transform feedback vertex
64 6a06a912 Leszek Koltunski
65 da681e7e Leszek Koltunski
   private static final int BYTES_PER_FLOAT = 4;
66 3ef3364d Leszek Koltunski
67 6f2d931d Leszek Koltunski
   private static final int OFFSET_POS = POS_ATTRIB*BYTES_PER_FLOAT;
68
   private static final int OFFSET_NOR = NOR_ATTRIB*BYTES_PER_FLOAT;
69
   private static final int OFFSET_INF = INF_ATTRIB*BYTES_PER_FLOAT;
70
   private static final int OFFSET_TEX = TEX_ATTRIB*BYTES_PER_FLOAT;
71 36d65d88 Leszek Koltunski
   private static final int OFFSET_COM = COM_ATTRIB*BYTES_PER_FLOAT;
72 bc208a9c Leszek Koltunski
73 227b9bca Leszek Koltunski
   private static final int TRAN_SIZE  = TRAN_ATTRIBS*BYTES_PER_FLOAT;
74 e54bfada Leszek Koltunski
   private static final int VERT1_SIZE = VERT1_ATTRIBS*BYTES_PER_FLOAT;
75
   private static final int VERT2_SIZE = VERT2_ATTRIBS*BYTES_PER_FLOAT;
76 a51fe521 Leszek Koltunski
77 e54bfada Leszek Koltunski
   private boolean mShowNormals;              // when rendering this mesh, draw normal vectors?
78
   private InternalBuffer mVBO1, mVBO2, mTFO; // main vertex buffer and transform feedback buffer
79 da681e7e Leszek Koltunski
   private int mNumVertices;
80 e54bfada Leszek Koltunski
   private float[] mVertAttribs1;             // packed: PosX,PosY,PosZ, NorX,NorY,NorZ, InfX,InfY,InfZ
81 36d65d88 Leszek Koltunski
   private float[] mVertAttribs2;             // packed: TexS,TexT, Component
82 7a5e538a Leszek Koltunski
   private float mInflate;
83 2aeb75aa Leszek Koltunski
   private int[] mEquAssociation;
84
   private int[] mAndAssociation;
85 36d65d88 Leszek Koltunski
86 71d8aba1 Leszek Koltunski
   DeferredJobs.JobNode[] mJobNode;
87 07206c71 Leszek Koltunski
88 2aeb75aa Leszek Koltunski
   private static int[] mEquAssociationH = new int[EffectQueue.MAIN_VARIANTS];
89
   private static int[] mAndAssociationH = new int[EffectQueue.MAIN_VARIANTS];
90 3ef3364d Leszek Koltunski
91 7e53a35f Leszek Koltunski
   private static class Component
92 c90aca24 Leszek Koltunski
     {
93
     private int mEndIndex;
94 a3a05347 Leszek Koltunski
     private Static4D mTextureMap;
95 c90aca24 Leszek Koltunski
96 0d4aae88 Leszek Koltunski
     Component(int end)
97 c90aca24 Leszek Koltunski
       {
98 a3a05347 Leszek Koltunski
       mEndIndex  = end;
99
       mTextureMap= new Static4D(0,0,1,1);
100 c90aca24 Leszek Koltunski
       }
101
     Component(Component original)
102
       {
103
       mEndIndex = original.mEndIndex;
104 a3a05347 Leszek Koltunski
105
       float x = original.mTextureMap.get0();
106
       float y = original.mTextureMap.get1();
107
       float z = original.mTextureMap.get2();
108
       float w = original.mTextureMap.get3();
109
       mTextureMap = new Static4D(x,y,z,w);
110 0d4aae88 Leszek Koltunski
       }
111
112 a3a05347 Leszek Koltunski
     void setMap(Static4D map)
113 0d4aae88 Leszek Koltunski
       {
114 a3a05347 Leszek Koltunski
       mTextureMap.set(map.get0(),map.get1(),map.get2(),map.get3());
115 c90aca24 Leszek Koltunski
       }
116
     }
117
118
   private ArrayList<Component> mComponent;
119
120 6a06a912 Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
121 3ef3364d Leszek Koltunski
122 0f10a0b6 Leszek Koltunski
   MeshBase()
123 3ef3364d Leszek Koltunski
     {
124 4f81e0c8 Leszek Koltunski
     mShowNormals= false;
125
     mInflate    = 0.0f;
126
     mComponent  = new ArrayList<>();
127 2aeb75aa Leszek Koltunski
     mEquAssociation= new int[MAX_COMPONENTS];
128
     mAndAssociation= new int[MAX_COMPONENTS];
129 36d65d88 Leszek Koltunski
130 71d8aba1 Leszek Koltunski
     mJobNode = new DeferredJobs.JobNode[1];
131
132 2aeb75aa Leszek Koltunski
     for(int i=0; i<MAX_COMPONENTS; i++)
133
       {
134
       mAndAssociation[i] = DEFAULT_ASSOCIATION;
135
       mEquAssociation[i] = i;
136
       }
137 4f81e0c8 Leszek Koltunski
138 e54bfada Leszek Koltunski
     mVBO1= new InternalBuffer(GLES30.GL_ARRAY_BUFFER             , GLES30.GL_STATIC_READ);
139
     mVBO2= new InternalBuffer(GLES30.GL_ARRAY_BUFFER             , GLES30.GL_STATIC_READ);
140 b7074bc6 Leszek Koltunski
     mTFO = new InternalBuffer(GLES30.GL_TRANSFORM_FEEDBACK_BUFFER, GLES30.GL_STATIC_READ);
141 c90aca24 Leszek Koltunski
     }
142
143
///////////////////////////////////////////////////////////////////////////////////////////////////
144
// copy constructor
145
146 4f81e0c8 Leszek Koltunski
   MeshBase(MeshBase original, boolean deep)
147 c90aca24 Leszek Koltunski
     {
148 1fad573e Leszek Koltunski
     mShowNormals= original.mShowNormals;
149
     mInflate    = original.mInflate;
150
     mNumVertices= original.mNumVertices;
151 42571056 Leszek Koltunski
152 2aeb75aa Leszek Koltunski
     mAndAssociation= new int[MAX_COMPONENTS];
153
     System.arraycopy(original.mAndAssociation, 0, mAndAssociation, 0, MAX_COMPONENTS);
154
     mEquAssociation= new int[MAX_COMPONENTS];
155
     System.arraycopy(original.mEquAssociation, 0, mEquAssociation, 0, MAX_COMPONENTS);
156 36d65d88 Leszek Koltunski
157 4f81e0c8 Leszek Koltunski
     if( deep )
158
       {
159 71d8aba1 Leszek Koltunski
       mJobNode = new DeferredJobs.JobNode[1];
160 1fad573e Leszek Koltunski
       if( original.mJobNode[0]==null ) copy(original);
161
       else mJobNode[0] = DeferredJobs.copy(this,original);
162 4f81e0c8 Leszek Koltunski
       }
163
     else
164
       {
165 71d8aba1 Leszek Koltunski
       mJobNode      = original.mJobNode;
166
       mVBO1         = original.mVBO1;
167
       mVertAttribs1 = original.mVertAttribs1;
168 1fad573e Leszek Koltunski
       shallowCopy(original);
169 4f81e0c8 Leszek Koltunski
       }
170 cbd502ec Leszek Koltunski
171 4f81e0c8 Leszek Koltunski
     mTFO = new InternalBuffer(GLES30.GL_TRANSFORM_FEEDBACK_BUFFER, GLES30.GL_STATIC_READ);
172 cbd502ec Leszek Koltunski
     mTFO.invalidate();
173 42571056 Leszek Koltunski
     }
174
175 36d65d88 Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
176
177 1fad573e Leszek Koltunski
   void copy(MeshBase original)
178 36d65d88 Leszek Koltunski
     {
179 1fad573e Leszek Koltunski
     shallowCopy(original);
180
181
     mVBO1= new InternalBuffer(GLES30.GL_ARRAY_BUFFER, GLES30.GL_STATIC_READ);
182
     mVertAttribs1= new float[mNumVertices*VERT1_ATTRIBS];
183
     System.arraycopy(original.mVertAttribs1,0,mVertAttribs1,0,mNumVertices*VERT1_ATTRIBS);
184
     mVBO1.invalidate();
185 36d65d88 Leszek Koltunski
     }
186
187
///////////////////////////////////////////////////////////////////////////////////////////////////
188
189 1fad573e Leszek Koltunski
   private void shallowCopy(MeshBase original)
190 36d65d88 Leszek Koltunski
     {
191 1fad573e Leszek Koltunski
     int size = original.mComponent.size();
192
     mComponent = new ArrayList<>();
193 36d65d88 Leszek Koltunski
194 1fad573e Leszek Koltunski
     for(int i=0; i<size; i++)
195
       {
196
       Component comp = new Component(original.mComponent.get(i));
197
       mComponent.add(comp);
198
       }
199 f4c5a46e Leszek Koltunski
200 1fad573e Leszek Koltunski
     mVBO2= new InternalBuffer(GLES30.GL_ARRAY_BUFFER, GLES30.GL_STATIC_READ);
201
     mVertAttribs2= new float[mNumVertices*VERT2_ATTRIBS];
202
     System.arraycopy(original.mVertAttribs2,0,mVertAttribs2,0,mNumVertices*VERT2_ATTRIBS);
203
     mVBO2.invalidate();
204 f4c5a46e Leszek Koltunski
     }
205
206 a8dfedcc Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
207
208
   void merge()
209
     {
210
     int num = mComponent.size();
211
212
     if( num>1 )
213
       {
214
       mComponent.clear();
215
       mComponent.add(new Component(mNumVertices-1));
216
217
       for(int index=0; index<mNumVertices; index++)
218
         {
219
         mVertAttribs2[VERT2_ATTRIBS*index+COM_ATTRIB] = 0;
220
         }
221
222
       mVBO2.invalidate();
223
       }
224
     }
225
226 0d4aae88 Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
227
228
   int numComponents()
229
     {
230
     return mComponent.size();
231
     }
232
233 42571056 Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
234 6c00149d Leszek Koltunski
// when a derived class is done computing its mesh, it has to call this method.
235 42571056 Leszek Koltunski
236 e54bfada Leszek Koltunski
   void setAttribs(float[] vert1Attribs, float[] vert2Attribs)
237 42571056 Leszek Koltunski
     {
238 e54bfada Leszek Koltunski
     mNumVertices = vert1Attribs.length/VERT1_ATTRIBS;
239
     mVertAttribs1= vert1Attribs;
240
     mVertAttribs2= vert2Attribs;
241 da681e7e Leszek Koltunski
242 36d65d88 Leszek Koltunski
     mComponent.add(new Component(mNumVertices-1));
243 c90aca24 Leszek Koltunski
244 e54bfada Leszek Koltunski
     mVBO1.invalidate();
245
     mVBO2.invalidate();
246 42571056 Leszek Koltunski
     }
247
248
///////////////////////////////////////////////////////////////////////////////////////////////////
249
250 1fad573e Leszek Koltunski
   void joinAttribs(MeshBase[] meshes)
251 226144d0 leszek
     {
252 0d4aae88 Leszek Koltunski
     MeshBase mesh;
253 1fad573e Leszek Koltunski
     Component comp;
254 a8dfedcc Leszek Koltunski
     int numMeshes = meshes.length;
255 1fad573e Leszek Koltunski
     int origVertices = mNumVertices;
256
     int origComponents=0,numComponents,numVertices;
257 044b5494 Leszek Koltunski
258 0d4aae88 Leszek Koltunski
     if( origVertices>0 )
259
       {
260 1fad573e Leszek Koltunski
       origComponents = mComponent.size();
261
       mNumVertices+= ( mNumVertices%2==1 ? 2:1 );
262
       mComponent.get(origComponents-1).mEndIndex = mNumVertices-1;
263 0d4aae88 Leszek Koltunski
       }
264 044b5494 Leszek Koltunski
265 e7f85322 Leszek Koltunski
     for(int i=0; i<numMeshes; i++)
266 0d4aae88 Leszek Koltunski
       {
267
       mesh = meshes[i];
268 1fad573e Leszek Koltunski
       numComponents = mesh.mComponent.size();
269 36d65d88 Leszek Koltunski
       numVertices = mesh.mNumVertices;
270
271 1fad573e Leszek Koltunski
       int extraVerticesBefore = mNumVertices==0 ? 0:1;
272
       int extraVerticesAfter  = (i==numMeshes-1) ? 0 : (numVertices%2==1 ? 2:1);
273 36d65d88 Leszek Koltunski
274 1fad573e Leszek Koltunski
       for(int j=0; j<numComponents; j++)
275 0d4aae88 Leszek Koltunski
         {
276 1fad573e Leszek Koltunski
         comp = new Component(mesh.mComponent.get(j));
277
         comp.mEndIndex += (extraVerticesBefore+mNumVertices+extraVerticesAfter);
278
         mComponent.add(comp);
279 23b733db Leszek Koltunski
280 1fad573e Leszek Koltunski
         if( origComponents<MAX_COMPONENTS )
281 36d65d88 Leszek Koltunski
           {
282 2aeb75aa Leszek Koltunski
           mAndAssociation[origComponents] = mesh.mAndAssociation[j];
283
           mEquAssociation[origComponents] = mesh.mEquAssociation[j];
284 1fad573e Leszek Koltunski
           origComponents++;
285 36d65d88 Leszek Koltunski
           }
286 e7f85322 Leszek Koltunski
         }
287 a8dfedcc Leszek Koltunski
288 1fad573e Leszek Koltunski
       mNumVertices += (extraVerticesBefore+numVertices+extraVerticesAfter);
289
       }
290 a8dfedcc Leszek Koltunski
291 1fad573e Leszek Koltunski
     float[] newAttribs1 = new float[VERT1_ATTRIBS*mNumVertices];
292 e54bfada Leszek Koltunski
     float[] newAttribs2 = new float[VERT2_ATTRIBS*mNumVertices];
293 1fad573e Leszek Koltunski
     numVertices = origVertices;
294 0d4aae88 Leszek Koltunski
295
     if( origVertices>0 )
296
       {
297 1fad573e Leszek Koltunski
       System.arraycopy(mVertAttribs1,                              0, newAttribs1,                         0, VERT1_ATTRIBS*numVertices);
298
       System.arraycopy(mVertAttribs1, VERT1_ATTRIBS*(origVertices-1), newAttribs1, VERT1_ATTRIBS*origVertices, VERT1_ATTRIBS    );
299 e54bfada Leszek Koltunski
       System.arraycopy(mVertAttribs2,                              0, newAttribs2,                         0, VERT2_ATTRIBS*numVertices);
300
       System.arraycopy(mVertAttribs2, VERT2_ATTRIBS*(origVertices-1), newAttribs2, VERT2_ATTRIBS*origVertices, VERT2_ATTRIBS    );
301 0d4aae88 Leszek Koltunski
       origVertices++;
302
303 e7f85322 Leszek Koltunski
       if( numVertices%2==1 )
304 0d4aae88 Leszek Koltunski
         {
305 1fad573e Leszek Koltunski
         System.arraycopy(mVertAttribs1, VERT1_ATTRIBS*(origVertices-1), newAttribs1, VERT1_ATTRIBS*origVertices, VERT1_ATTRIBS);
306 e54bfada Leszek Koltunski
         System.arraycopy(mVertAttribs2, VERT2_ATTRIBS*(origVertices-1), newAttribs2, VERT2_ATTRIBS*origVertices, VERT2_ATTRIBS);
307 0d4aae88 Leszek Koltunski
         origVertices++;
308
         }
309
       }
310
311 e7f85322 Leszek Koltunski
     for(int i=0; i<numMeshes; i++)
312 0d4aae88 Leszek Koltunski
       {
313
       mesh = meshes[i];
314 e7f85322 Leszek Koltunski
       numVertices = mesh.mNumVertices;
315 0d4aae88 Leszek Koltunski
316 22e60fba Leszek Koltunski
       if( origVertices>0 )
317
         {
318 1fad573e Leszek Koltunski
         System.arraycopy(mesh.mVertAttribs1, 0, newAttribs1, VERT1_ATTRIBS*origVertices, VERT1_ATTRIBS    );
319 e54bfada Leszek Koltunski
         System.arraycopy(mesh.mVertAttribs2, 0, newAttribs2, VERT2_ATTRIBS*origVertices, VERT2_ATTRIBS    );
320 22e60fba Leszek Koltunski
         origVertices++;
321
         }
322 1fad573e Leszek Koltunski
       System.arraycopy(mesh.mVertAttribs1, 0, newAttribs1, VERT1_ATTRIBS*origVertices, VERT1_ATTRIBS*numVertices);
323 e54bfada Leszek Koltunski
       System.arraycopy(mesh.mVertAttribs2, 0, newAttribs2, VERT2_ATTRIBS*origVertices, VERT2_ATTRIBS*numVertices);
324 e7f85322 Leszek Koltunski
       origVertices+=numVertices;
325 0d4aae88 Leszek Koltunski
326 e7f85322 Leszek Koltunski
       if( i<numMeshes-1 )
327 0d4aae88 Leszek Koltunski
         {
328 1fad573e Leszek Koltunski
         System.arraycopy(mesh.mVertAttribs1, VERT1_ATTRIBS*(numVertices-1), newAttribs1, VERT1_ATTRIBS*origVertices, VERT1_ATTRIBS);
329 e54bfada Leszek Koltunski
         System.arraycopy(mesh.mVertAttribs2, VERT2_ATTRIBS*(numVertices-1), newAttribs2, VERT2_ATTRIBS*origVertices, VERT2_ATTRIBS);
330 0d4aae88 Leszek Koltunski
         origVertices++;
331
332 e7f85322 Leszek Koltunski
         if( numVertices%2==1 )
333 0d4aae88 Leszek Koltunski
           {
334 1fad573e Leszek Koltunski
           System.arraycopy(mesh.mVertAttribs1, VERT1_ATTRIBS*(numVertices-1), newAttribs1, VERT1_ATTRIBS*origVertices, VERT1_ATTRIBS);
335 e54bfada Leszek Koltunski
           System.arraycopy(mesh.mVertAttribs2, VERT2_ATTRIBS*(numVertices-1), newAttribs2, VERT2_ATTRIBS*origVertices, VERT2_ATTRIBS);
336 0d4aae88 Leszek Koltunski
           origVertices++;
337
           }
338
         }
339
       }
340
341
     if( origVertices!=mNumVertices )
342
       {
343
       android.util.Log.e("mesh", "join: origVertices: "+origVertices+" numVertices: "+mNumVertices);
344
       }
345
346 36d65d88 Leszek Koltunski
     int endIndex, index=0, numComp = mComponent.size();
347
348
     for(int component=0; component<numComp; component++)
349
       {
350
       endIndex = mComponent.get(component).mEndIndex;
351
352
       for( ; index<=endIndex; index++) newAttribs2[VERT2_ATTRIBS*index+COM_ATTRIB] = component;
353
       }
354
355 1fad573e Leszek Koltunski
     mVertAttribs1 = newAttribs1;
356 e54bfada Leszek Koltunski
     mVertAttribs2 = newAttribs2;
357 1fad573e Leszek Koltunski
     mVBO1.invalidate();
358 e54bfada Leszek Koltunski
     mVBO2.invalidate();
359 23b733db Leszek Koltunski
     }
360
361 a8dfedcc Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
362
// called from MeshJoined
363
364
   void join(MeshBase[] meshes)
365
     {
366 1fad573e Leszek Koltunski
     boolean immediateJoin = true;
367 a8dfedcc Leszek Koltunski
368 1fad573e Leszek Koltunski
     for (MeshBase mesh : meshes)
369 a8dfedcc Leszek Koltunski
       {
370 1fad573e Leszek Koltunski
       if (mesh.mJobNode[0] != null)
371
         {
372
         immediateJoin = false;
373
         break;
374
         }
375 a8dfedcc Leszek Koltunski
       }
376
377 1fad573e Leszek Koltunski
     if( immediateJoin ) joinAttribs(meshes);
378
     else                mJobNode[0] = DeferredJobs.join(this,meshes);
379
     }
380 a8dfedcc Leszek Koltunski
381 1fad573e Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
382 a8dfedcc Leszek Koltunski
383 1fad573e Leszek Koltunski
   void textureMap(Static4D[] maps)
384
     {
385
     int num_comp = mComponent.size();
386
     int num_maps = maps.length;
387
     int min = Math.min(num_comp, num_maps);
388
     int vertex = 0;
389
     Static4D newMap, oldMap;
390
     Component comp;
391
     float newW, newH, ratW, ratH, movX, movY;
392 a8dfedcc Leszek Koltunski
393 1fad573e Leszek Koltunski
     for(int i=0; i<min; i++)
394
       {
395
       newMap = maps[i];
396
       comp = mComponent.get(i);
397
398
       if( newMap!=null )
399 a8dfedcc Leszek Koltunski
         {
400 1fad573e Leszek Koltunski
         newW = newMap.get2();
401
         newH = newMap.get3();
402 a8dfedcc Leszek Koltunski
403 1fad573e Leszek Koltunski
         if( newW!=0.0f && newH!=0.0f )
404 a8dfedcc Leszek Koltunski
           {
405 1fad573e Leszek Koltunski
           oldMap = comp.mTextureMap;
406
           ratW = newW/oldMap.get2();
407
           ratH = newH/oldMap.get3();
408
           movX = newMap.get0() - ratW*oldMap.get0();
409
           movY = newMap.get1() - ratH*oldMap.get1();
410
411
           for( int index=vertex*VERT2_ATTRIBS+TEX_ATTRIB ; vertex<=comp.mEndIndex; vertex++, index+=VERT2_ATTRIBS)
412
             {
413
             mVertAttribs2[index  ] = ratW*mVertAttribs2[index  ] + movX;
414
             mVertAttribs2[index+1] = ratH*mVertAttribs2[index+1] + movY;
415
             }
416
           comp.setMap(newMap);
417 a8dfedcc Leszek Koltunski
           }
418
         }
419
420 1fad573e Leszek Koltunski
       vertex= comp.mEndIndex+1;
421 a8dfedcc Leszek Koltunski
       }
422
423 1fad573e Leszek Koltunski
     mVBO2.invalidate();
424
     }
425
426
///////////////////////////////////////////////////////////////////////////////////////////////////
427 a8dfedcc Leszek Koltunski
428 1fad573e Leszek Koltunski
   public static int getMaxComponents()
429
     {
430
     return MAX_COMPONENTS;
431
     }
432
433
///////////////////////////////////////////////////////////////////////////////////////////////////
434
435
   public static void getUniforms(int mProgramH, int variant)
436
     {
437 2aeb75aa Leszek Koltunski
     mEquAssociationH[variant] = GLES30.glGetUniformLocation( mProgramH, "vComEquAssoc");
438
     mAndAssociationH[variant] = GLES30.glGetUniformLocation( mProgramH, "vComAndAssoc");
439 a8dfedcc Leszek Koltunski
     }
440
441 f046b159 Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
442
/**
443
 * Not part of public API, do not document (public only because has to be used from the main package)
444
 *
445
 * @y.exclude
446
 */
447
   public void copyTransformToVertex()
448
     {
449 e54bfada Leszek Koltunski
     ByteBuffer buffer = (ByteBuffer)GLES30.glMapBufferRange( GLES30.GL_TRANSFORM_FEEDBACK_BUFFER, 0,
450
                                                              TRAN_SIZE*mNumVertices, GLES30.GL_MAP_READ_BIT);
451 f046b159 Leszek Koltunski
     if( buffer!=null )
452
       {
453 e54bfada Leszek Koltunski
       FloatBuffer feedback = buffer.order(ByteOrder.nativeOrder()).asFloatBuffer();
454
       feedback.get(mVertAttribs1,0,VERT1_ATTRIBS*mNumVertices);
455
       mVBO1.update(mVertAttribs1);
456 f046b159 Leszek Koltunski
       }
457
     else
458
       {
459 b5be333a Leszek Koltunski
       int error = GLES30.glGetError();
460
       Log.e("mesh", "failed to map tf buffer, error="+error);
461 f046b159 Leszek Koltunski
       }
462
463 b5be333a Leszek Koltunski
     GLES30.glUnmapBuffer(GLES30.GL_TRANSFORM_FEEDBACK);
464 f046b159 Leszek Koltunski
     }
465
466 1fad573e Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
467
/**
468
 * Not part of public API, do not document (public only because has to be used from the main package)
469
 *
470
 * @y.exclude
471
 */
472
   public void debug()
473
     {
474
     if( mJobNode[0]!=null )
475
       {
476
       mJobNode[0].print(0);
477
       }
478
     else
479
       {
480
       android.util.Log.e("mesh", "JobNode null");
481
       }
482
     }
483
484
///////////////////////////////////////////////////////////////////////////////////////////////////
485
/**
486
 * Not part of public API, do not document (public only because has to be used from the main package)
487
 *
488
 * @y.exclude
489
 */
490
   public void print()
491
     {
492
     StringBuffer sb = new StringBuffer();
493
494
     for(int i=0; i<mNumVertices; i++)
495
       {
496
       sb.append('(');
497
       sb.append(mVertAttribs1[VERT1_ATTRIBS*i+POS_ATTRIB  ]);
498
       sb.append(',');
499
       sb.append(mVertAttribs1[VERT1_ATTRIBS*i+POS_ATTRIB+1]);
500
       sb.append(',');
501
       sb.append(mVertAttribs1[VERT1_ATTRIBS*i+POS_ATTRIB+2]);
502
       sb.append(") ");
503
       }
504
505
     StringBuffer sb2 = new StringBuffer();
506
507
     for(int i=0; i<mNumVertices; i++)
508
       {
509
       sb2.append(mVertAttribs2[VERT2_ATTRIBS*i+COM_ATTRIB]);
510
       sb2.append(' ');
511
       }
512
513
     Log.d("mesh", sb.toString()+"\n"+sb2.toString());
514
     }
515
516 23b733db Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
517
/**
518 0d4aae88 Leszek Koltunski
 * Not part of public API, do not document (public only because has to be used from the main package)
519
 *
520
 * @y.exclude
521 23b733db Leszek Koltunski
 */
522 0d4aae88 Leszek Koltunski
   public int getTFO()
523 23b733db Leszek Koltunski
     {
524 b5be333a Leszek Koltunski
     return mTFO.createImmediately(mNumVertices*TRAN_SIZE, null);
525 23b733db Leszek Koltunski
     }
526
527
///////////////////////////////////////////////////////////////////////////////////////////////////
528
/**
529 0d4aae88 Leszek Koltunski
 * Not part of public API, do not document (public only because has to be used from the main package)
530
 *
531
 * @y.exclude
532 23b733db Leszek Koltunski
 */
533 0d4aae88 Leszek Koltunski
   public int getNumVertices()
534 23b733db Leszek Koltunski
     {
535 0d4aae88 Leszek Koltunski
     return mNumVertices;
536 23b733db Leszek Koltunski
     }
537
538 36d65d88 Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
539
/**
540
 * Not part of public API, do not document (public only because has to be used from the main package)
541
 *
542
 * @y.exclude
543
 */
544
   public void send(int variant)
545
     {
546 2aeb75aa Leszek Koltunski
     GLES30.glUniform1iv( mEquAssociationH[variant], MAX_COMPONENTS, mEquAssociation, 0);
547
     GLES30.glUniform1iv( mAndAssociationH[variant], MAX_COMPONENTS, mAndAssociation, 0);
548 36d65d88 Leszek Koltunski
     }
549
550 044b5494 Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
551 6c00149d Leszek Koltunski
/**
552
 * Not part of public API, do not document (public only because has to be used from the main package)
553
 *
554
 * @y.exclude
555
 */
556 da681e7e Leszek Koltunski
   public void bindVertexAttribs(DistortedProgram program)
557 6c00149d Leszek Koltunski
     {
558 71d8aba1 Leszek Koltunski
     if( mJobNode[0]!=null )
559 f046b159 Leszek Koltunski
       {
560 71d8aba1 Leszek Koltunski
       mJobNode[0].execute();  // this will set itself to null
561 f046b159 Leszek Koltunski
       }
562
563 e54bfada Leszek Koltunski
     int index1 = mVBO1.createImmediately(mNumVertices*VERT1_SIZE, mVertAttribs1);
564
     int index2 = mVBO2.createImmediately(mNumVertices*VERT2_SIZE, mVertAttribs2);
565 22e60fba Leszek Koltunski
566 e54bfada Leszek Koltunski
     GLES30.glBindBuffer(GLES30.GL_ARRAY_BUFFER, index1 );
567
     GLES30.glVertexAttribPointer(program.mAttribute[0], POS_DATA_SIZE, GLES30.GL_FLOAT, false, VERT1_SIZE, OFFSET_POS);
568
     GLES30.glVertexAttribPointer(program.mAttribute[1], NOR_DATA_SIZE, GLES30.GL_FLOAT, false, VERT1_SIZE, OFFSET_NOR);
569
     GLES30.glVertexAttribPointer(program.mAttribute[2], INF_DATA_SIZE, GLES30.GL_FLOAT, false, VERT1_SIZE, OFFSET_INF);
570
     GLES30.glBindBuffer(GLES30.GL_ARRAY_BUFFER, index2 );
571
     GLES30.glVertexAttribPointer(program.mAttribute[3], TEX_DATA_SIZE, GLES30.GL_FLOAT, false, VERT2_SIZE, OFFSET_TEX);
572 36d65d88 Leszek Koltunski
     GLES30.glVertexAttribPointer(program.mAttribute[4], COM_DATA_SIZE, GLES30.GL_FLOAT, false, VERT2_SIZE, OFFSET_COM);
573 b7074bc6 Leszek Koltunski
     GLES30.glBindBuffer(GLES30.GL_ARRAY_BUFFER, 0);
574 da681e7e Leszek Koltunski
     }
575
576
///////////////////////////////////////////////////////////////////////////////////////////////////
577
/**
578
 * Not part of public API, do not document (public only because has to be used from the main package)
579
 *
580
 * @y.exclude
581
 */
582
   public void bindTransformAttribs(DistortedProgram program)
583
     {
584 7e53a35f Leszek Koltunski
     int index = mTFO.createImmediately(mNumVertices*TRAN_SIZE, null);
585 22e60fba Leszek Koltunski
586 b7074bc6 Leszek Koltunski
     GLES30.glBindBuffer(GLES30.GL_ARRAY_BUFFER, index );
587
     GLES30.glVertexAttribPointer(program.mAttribute[0], POS_DATA_SIZE, GLES30.GL_FLOAT, false, 0, 0);
588
     GLES30.glBindBuffer(GLES30.GL_ARRAY_BUFFER, 0);
589 6c00149d Leszek Koltunski
     }
590
591 7a5e538a Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
592
/**
593
 * Not part of public API, do not document (public only because has to be used from the main package)
594
 *
595
 * @y.exclude
596
 */
597
   public void setInflate(float inflate)
598
     {
599
     mInflate = inflate;
600
     }
601
602
///////////////////////////////////////////////////////////////////////////////////////////////////
603
/**
604
 * Not part of public API, do not document (public only because has to be used from the main package)
605
 *
606
 * @y.exclude
607
 */
608
   public float getInflate()
609
     {
610
     return mInflate;
611
     }
612
613 466450b5 Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
614
// PUBLIC API
615 3fc9327a Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
616
/**
617
 * When rendering this Mesh, do we want to render the Normal vectors as well?
618 420836fc leszek
 * <p>
619
 * Will work only on OpenGL ES >= 3.0 devices.
620 3fc9327a Leszek Koltunski
 *
621
 * @param show Controls if we render the Normal vectors or not.
622
 */
623
   public void setShowNormals(boolean show)
624
     {
625 b7074bc6 Leszek Koltunski
     mShowNormals = show;
626 3fc9327a Leszek Koltunski
     }
627 466450b5 Leszek Koltunski
628 6c00149d Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
629
/**
630
 * When rendering this mesh, should we also draw the normal vectors?
631
 *
632
 * @return <i>true</i> if we do render normal vectors
633
 */
634
   public boolean getShowNormals()
635
     {
636
     return mShowNormals;
637
     }
638
639 a8dfedcc Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
640
/**
641
 * Merge all components of this Mesh into a single one.
642
 */
643
   public void mergeComponents()
644
     {
645 1fad573e Leszek Koltunski
     if( mJobNode[0]==null )
646 a8dfedcc Leszek Koltunski
       {
647
       merge();
648
       }
649
     else
650
       {
651
       mJobNode[0] = DeferredJobs.merge(this);
652
       }
653
     }
654
655 466450b5 Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
656
/**
657
 * Release all internal resources.
658
 */
659
   public void markForDeletion()
660
     {
661 e54bfada Leszek Koltunski
     mVertAttribs1 = null;
662
     mVertAttribs2 = null;
663 466450b5 Leszek Koltunski
664 e54bfada Leszek Koltunski
     mVBO1.markForDeletion();
665
     mVBO2.markForDeletion();
666 466450b5 Leszek Koltunski
     mTFO.markForDeletion();
667
     }
668 fa8bc998 Leszek Koltunski
669
///////////////////////////////////////////////////////////////////////////////////////////////////
670
/**
671 f046b159 Leszek Koltunski
 * Apply a Vertex Effect to the vertex mesh.
672 fa8bc998 Leszek Koltunski
 * <p>
673 c90aca24 Leszek Koltunski
 * This is a static, permanent modification of the vertices contained in this Mesh. If the effects
674 f046b159 Leszek Koltunski
 * contain any Dynamics, the Dynamics will be evaluated at 0.
675 fa8bc998 Leszek Koltunski
 *
676 f046b159 Leszek Koltunski
 * We would call this several times building up a list of Effects to do. This list of effects gets
677
 * lazily executed only when the Mesh is used for rendering for the first time.
678 e172985c Leszek Koltunski
 *
679 f046b159 Leszek Koltunski
 * @param effect Vertex Effect to apply to the Mesh.
680 fa8bc998 Leszek Koltunski
 */
681 f046b159 Leszek Koltunski
   public void apply(VertexEffect effect)
682 fa8bc998 Leszek Koltunski
     {
683 71d8aba1 Leszek Koltunski
     mJobNode[0] = DeferredJobs.vertex(this,effect);
684 c90aca24 Leszek Koltunski
     }
685
686
///////////////////////////////////////////////////////////////////////////////////////////////////
687
/**
688 a3a05347 Leszek Koltunski
 * Sets texture maps for (some of) the components of this mesh.
689 c90aca24 Leszek Koltunski
 * <p>
690 a3a05347 Leszek Koltunski
 * Format: ( x of lower-left corner, y of lower-left corner, width, height ).
691
 * For example maps[0] = new Static4D( 0.0, 0.5, 0.5, 0.5 ) sets the 0th component texture map to the
692 0d4aae88 Leszek Koltunski
 * upper-left quadrant of the texture.
693 a3a05347 Leszek Koltunski
 * <p>
694
 * Probably the most common user case would be sending as many maps as there are components in this
695
 * Mesh. One can also send less, or more (the extraneous ones will be ignored) and set some of them
696
 * to null (those will be ignored as well). So if there are 5 components, and we want to set the map
697
 * of the 2nd and 4rd one, call this with
698
 * maps = new Static4D[4]
699
 * maps[0] = null
700
 * maps[1] = the map for the 2nd component
701
 * maps[2] = null
702
 * maps[3] = the map for the 4th component
703
 *
704
 * A map's width and height have to be non-zero (but can be negative!)
705 e172985c Leszek Koltunski
 *
706
 * @param maps List of texture maps to apply to the texture's components.
707 c90aca24 Leszek Koltunski
 */
708 a3a05347 Leszek Koltunski
   public void setTextureMap(Static4D[] maps)
709 c90aca24 Leszek Koltunski
     {
710 1fad573e Leszek Koltunski
     if( mJobNode[0]==null )
711 ea88d502 Leszek Koltunski
       {
712 1fad573e Leszek Koltunski
       textureMap(maps);
713
       }
714
     else
715
       {
716
       mJobNode[0] = DeferredJobs.textureMap(this,maps);
717 ea88d502 Leszek Koltunski
       }
718 fa8bc998 Leszek Koltunski
     }
719 9099e567 Leszek Koltunski
720 e172985c Leszek Koltunski
///////////////////////////////////////////////////////////////////////////////////////////////////
721
/**
722
 * Return the texture map of one of the components.
723
 *
724
 * @param component The component number whose texture map we want to retrieve.
725
 */
726
   public Static4D getTextureMap(int component)
727
     {
728
     return (component>=0 && component<mComponent.size()) ? mComponent.get(component).mTextureMap : null;
729
     }
730 cbd502ec Leszek Koltunski
731
///////////////////////////////////////////////////////////////////////////////////////////////////
732
/**
733 1e672c1d Leszek Koltunski
 * Set Effect association.
734 bc208a9c Leszek Koltunski
 *
735 1e672c1d Leszek Koltunski
 * This creates an association between a Component of this Mesh and a Vertex Effect.
736 2aeb75aa Leszek Koltunski
 * One can set two types of associations - an 'logical and' and a 'equal' associations and the Effect
737
 * will only be active on vertices of Components such that
738 36d65d88 Leszek Koltunski
 *
739 2aeb75aa Leszek Koltunski
 * (effect andAssoc) & (component andAssoc) != 0 || (effect equAssoc) == (mesh equAssoc)
740 36d65d88 Leszek Koltunski
 *
741
 * (see main_vertex_shader)
742 bc208a9c Leszek Koltunski
 *
743
 * The point: this way we can configure the system so that each Vertex Effect acts only on a certain
744 1e672c1d Leszek Koltunski
 * subset of a Mesh, thus potentially significantly reducing the number of render calls.
745 cbd502ec Leszek Koltunski
 */
746 2aeb75aa Leszek Koltunski
  public void setEffectAssociation(int component, int andAssociation, int equAssociation)
747 bc208a9c Leszek Koltunski
    {
748 36d65d88 Leszek Koltunski
    if( component>=0 && component<MAX_COMPONENTS )
749 bc208a9c Leszek Koltunski
      {
750 2aeb75aa Leszek Koltunski
      mAndAssociation[component] = andAssociation;
751
      mEquAssociation[component] = equAssociation;
752 bc208a9c Leszek Koltunski
      }
753
    }
754
755
///////////////////////////////////////////////////////////////////////////////////////////////////
756
/**
757 4f81e0c8 Leszek Koltunski
 * Copy the Mesh.
758
 *
759
 * @param deep If to be a deep or shallow copy of mVertAttribs1, i.e. the array holding vertices,
760
 *             normals and inflates (the rest, in particular the mVertAttribs2 containing texture
761 36d65d88 Leszek Koltunski
 *             coordinates and effect associations, is always deep copied)
762 bc208a9c Leszek Koltunski
 */
763 4f81e0c8 Leszek Koltunski
   public abstract MeshBase copy(boolean deep);
764 bc208a9c Leszek Koltunski
   }