Project

General

Profile

« Previous | Next » 

Revision 0bd9f644

Added by Leszek Koltunski over 3 years ago

Introduce an UBO to the vertex shader holding info about mesh effect associations.

View differences:

src/main/java/org/distorted/library/mesh/MeshBase.java
25 25

  
26 26
import org.distorted.library.effect.MatrixEffect;
27 27
import org.distorted.library.effect.VertexEffect;
28
import org.distorted.library.effectqueue.EffectQueue;
29 28
import org.distorted.library.main.InternalBuffer;
30 29
import org.distorted.library.program.DistortedProgram;
31 30
import org.distorted.library.type.Static4D;
......
47 46
 */
48 47
public abstract class MeshBase
49 48
   {
49
   private static final int UBO_BINDING = 1;
50 50
   private static final int MAX_EFFECT_COMPONENTS= 100;
51 51
   private static final int DEFAULT_ASSOCIATION = 0xffffffff;
52 52

  
......
79 79
   private static final int VERT1_SIZE = VERT1_ATTRIBS*BYTES_PER_FLOAT;
80 80
   private static final int VERT2_SIZE = VERT2_ATTRIBS*BYTES_PER_FLOAT;
81 81

  
82
   private static int mAssociationSize = 8*MAX_EFFECT_COMPONENTS;
83

  
82 84
   private boolean mShowNormals;              // when rendering this mesh, draw normal vectors?
83 85
   private InternalBuffer mVBO1, mVBO2, mTFO; // main vertex buffer and transform feedback buffer
86
   private InternalBuffer mUBO;               // Uniform Buffer Object
84 87
   private int mNumVertices;
85 88
   private float[] mVertAttribs1;             // packed: PosX,PosY,PosZ, NorX,NorY,NorZ, InfX,InfY,InfZ
86 89
   private float[] mVertAttribs2;             // packed: TexS,TexT, Component
87 90
   private float mInflate;
88
   private int[] mEquAssociation;
89
   private int[] mAndAssociation;
91
   private int[] mAssociations;
92
   private int mAssociationBlock;
93
   private boolean mNeedAdjustAssociation;
90 94

  
91 95
   DeferredJobs.JobNode[] mJobNode;
92 96

  
93
   private static int[] mEquAssociationH = new int[EffectQueue.MAIN_VARIANTS];
94
   private static int[] mAndAssociationH = new int[EffectQueue.MAIN_VARIANTS];
95

  
96 97
   private static final int TEX_COMP_SIZE = 5; // 5 four-bytes entities inside the component
97 98

  
98 99
   private static class TexComponent
......
134 135
     mTexComponent = new ArrayList<>();
135 136
     mEffComponent = new ArrayList<>();
136 137

  
137
     mEquAssociation= new int[MAX_EFFECT_COMPONENTS];
138
     mAndAssociation= new int[MAX_EFFECT_COMPONENTS];
138
     mNeedAdjustAssociation = true;
139
     mAssociationBlock = computeAssociationBlockSize();
140
     mAssociations= new int[mAssociationSize/4];
139 141

  
140 142
     mJobNode = new DeferredJobs.JobNode[1];
141 143

  
142 144
     for(int i=0; i<MAX_EFFECT_COMPONENTS; i++)
143 145
       {
144
       mAndAssociation[i] = DEFAULT_ASSOCIATION;
145
       mEquAssociation[i] = i;
146
       mAssociations[getAndIndex(i)] = DEFAULT_ASSOCIATION;
147
       mAssociations[getEquIndex(i)] = i;
146 148
       }
147 149

  
148 150
     mVBO1= new InternalBuffer(GLES30.GL_ARRAY_BUFFER             , GLES30.GL_STATIC_READ);
149 151
     mVBO2= new InternalBuffer(GLES30.GL_ARRAY_BUFFER             , GLES30.GL_STATIC_READ);
150 152
     mTFO = new InternalBuffer(GLES30.GL_TRANSFORM_FEEDBACK_BUFFER, GLES30.GL_STATIC_READ);
153
     mUBO = new InternalBuffer(GLES30.GL_UNIFORM_BUFFER           , GLES30.GL_STATIC_READ);
151 154
     }
152 155

  
153 156
///////////////////////////////////////////////////////////////////////////////////////////////////
......
159 162
     mInflate    = original.mInflate;
160 163
     mNumVertices= original.mNumVertices;
161 164

  
162
     mAndAssociation= new int[MAX_EFFECT_COMPONENTS];
163
     System.arraycopy(original.mAndAssociation, 0, mAndAssociation, 0, MAX_EFFECT_COMPONENTS);
164
     mEquAssociation= new int[MAX_EFFECT_COMPONENTS];
165
     System.arraycopy(original.mEquAssociation, 0, mEquAssociation, 0, MAX_EFFECT_COMPONENTS);
165
     mNeedAdjustAssociation = original.mNeedAdjustAssociation;
166
     mAssociationBlock = original.mAssociationBlock;
167

  
168
     int size = original.mAssociations.length;
169
     mAssociations= new int[size];
170
     System.arraycopy(original.mAssociations, 0, mAssociations, 0, size);
166 171

  
167 172
     if( deep )
168 173
       {
......
179 184
       }
180 185

  
181 186
     mTFO = new InternalBuffer(GLES30.GL_TRANSFORM_FEEDBACK_BUFFER, GLES30.GL_STATIC_READ);
182
     mTFO.invalidate();
187
     mUBO = new InternalBuffer(GLES30.GL_UNIFORM_BUFFER           , GLES30.GL_STATIC_READ);
188
     }
189

  
190
///////////////////////////////////////////////////////////////////////////////////////////////////
191
/**
192
 * @y.exclude
193
 */
194
   public static void setAssociationSize(int size)
195
     {
196
     mAssociationSize = size;
197
     }
198

  
199
///////////////////////////////////////////////////////////////////////////////////////////////////
200

  
201
   private int getAndIndex(int component)
202
     {
203
     return mAssociationBlock*component;
204
     }
205

  
206
///////////////////////////////////////////////////////////////////////////////////////////////////
207

  
208
   private int getEquIndex(int component)
209
     {
210
     return mAssociationBlock*(MAX_EFFECT_COMPONENTS+component);
211
     }
212

  
213
///////////////////////////////////////////////////////////////////////////////////////////////////
214

  
215
   private int computeAssociationBlockSize()
216
     {
217
     return 1 + (mAssociationSize/4 - 2*MAX_EFFECT_COMPONENTS) / (2*MAX_EFFECT_COMPONENTS-1);
218
     }
219

  
220
///////////////////////////////////////////////////////////////////////////////////////////////////
221
// The problem here is that at MeshBase object creation time, we might not know the size of the
222
// 'meshAssociation' Uniform Block Object in the vertex shader (the UBO is packed according to the
223
// 'shared' layout, which means the size of the block is known only after linking the shaders).
224
//
225
// We thus, in the constructor, guess that the layout will be tight (so we will need 8*MAX_EFFECT_C
226
// bytes there), allocate mAssociation already, and if later on, as a result of linking the shaders,
227
// we get a call to setAssociationSize() which changes the size to something else, we need to reallocate.
228
//
229
// It can happen that even before the linking the value of mAssociationSize is already 'right' because
230
// this is a static variable and it might persist from an earlier run. All the better then; this should
231
// never be wrong.
232

  
233
   private void adjustAssociation()
234
     {
235
     int oldLen = mAssociations.length;
236

  
237
     if( mAssociationSize != 4*oldLen )
238
       {
239
       int[] tmp = new int[oldLen];
240
       System.arraycopy(mAssociations, 0, tmp, 0, oldLen);
241

  
242
       int newLen = mAssociationSize/4;
243
       mAssociations = new int[newLen];
244
       mAssociationBlock = computeAssociationBlockSize();
245

  
246
       for(int i=0; i<oldLen/2; i++)
247
         {
248
         mAssociations[getAndIndex(i)] = tmp[i];                         // oldLen must be equal to
249
         mAssociations[getEquIndex(i)] = tmp[MAX_EFFECT_COMPONENTS+i];   // 8*MAX_EFFECT_COM
250
         }
251
       }
183 252
     }
184 253

  
185 254
///////////////////////////////////////////////////////////////////////////////////////////////////
......
270 339
       start = end+1;
271 340
       end   = mEffComponent.get(i);
272 341

  
273
       if( (andAssoc & mAndAssociation[i]) != 0 || (equAssoc == mEquAssociation[i]) )
342
       if( (andAssoc & mAssociations[getAndIndex(i)]) != 0 || (equAssoc == mAssociations[getEquIndex(i)]) )
274 343
         {
275 344
         applyMatrixToComponent(matrixP, matrixV, start, end);
276 345
         }
......
343 412

  
344 413
   void setEffectAssociationNow(int component, int andAssociation, int equAssociation)
345 414
     {
346
     mAndAssociation[component] = andAssociation;
347
     mEquAssociation[component] = equAssociation;
415
     mAssociations[getAndIndex(component)] = andAssociation;
416
     mAssociations[getEquIndex(component)] = equAssociation;
417

  
418
     mUBO.invalidate();
348 419
     }
349 420

  
350 421
///////////////////////////////////////////////////////////////////////////////////////////////////
......
410 481

  
411 482
         if( origEffComponents<MAX_EFFECT_COMPONENTS )
412 483
           {
413
           mAndAssociation[origEffComponents] = mesh.mAndAssociation[j];
414
           mEquAssociation[origEffComponents] = mesh.mEquAssociation[j];
484
           mAssociations[getAndIndex(origEffComponents)] = mesh.mAssociations[mesh.getAndIndex(j)];
485
           mAssociations[getEquIndex(origEffComponents)] = mesh.mAssociations[mesh.getEquIndex(j)];
415 486
           origEffComponents++;
416 487
           }
417 488
         }
......
561 632
     return MAX_EFFECT_COMPONENTS;
562 633
     }
563 634

  
564
///////////////////////////////////////////////////////////////////////////////////////////////////
565

  
566
   public static void getUniforms(int mProgramH, int variant)
567
     {
568
     mEquAssociationH[variant] = GLES30.glGetUniformLocation( mProgramH, "vComEquAssoc");
569
     mAndAssociationH[variant] = GLES30.glGetUniformLocation( mProgramH, "vComAndAssoc");
570
     }
571

  
572 635
///////////////////////////////////////////////////////////////////////////////////////////////////
573 636
/**
574 637
 * Not part of public API, do not document (public only because has to be used from the main package)
......
583 646
       {
584 647
       FloatBuffer feedback = buffer.order(ByteOrder.nativeOrder()).asFloatBuffer();
585 648
       feedback.get(mVertAttribs1,0,VERT1_ATTRIBS*mNumVertices);
586
       mVBO1.update(mVertAttribs1);
649
       mVBO1.updateFloat(mVertAttribs1);
587 650
       }
588 651
     else
589 652
       {
......
694 757
 */
695 758
   public int getTFO()
696 759
     {
697
     return mTFO.createImmediately(mNumVertices*TRAN_SIZE, null);
760
     return mTFO.createImmediatelyFloat(mNumVertices*TRAN_SIZE, null);
698 761
     }
699 762

  
700 763
///////////////////////////////////////////////////////////////////////////////////////////////////
......
714 777
 *
715 778
 * @y.exclude
716 779
 */
717
   public void send(int variant)
780
   public void send(int programH)
718 781
     {
719
     GLES30.glUniform1iv( mEquAssociationH[variant], MAX_EFFECT_COMPONENTS, mEquAssociation, 0);
720
     GLES30.glUniform1iv( mAndAssociationH[variant], MAX_EFFECT_COMPONENTS, mAndAssociation, 0);
782
     if( mNeedAdjustAssociation )
783
       {
784
       mNeedAdjustAssociation = false;
785
       adjustAssociation();
786
       }
787

  
788
     int index = mUBO.createImmediatelyInt( mAssociationSize, mAssociations);
789

  
790
     GLES30.glBindBufferBase(GLES30.GL_UNIFORM_BUFFER, UBO_BINDING, index);
791
     GLES30.glUniformBlockBinding(programH, UBO_BINDING, index);
721 792
     }
722 793

  
723 794
///////////////////////////////////////////////////////////////////////////////////////////////////
......
746 817
 */
747 818
       }
748 819

  
749
     int index1 = mVBO1.createImmediately(mNumVertices*VERT1_SIZE, mVertAttribs1);
750
     int index2 = mVBO2.createImmediately(mNumVertices*VERT2_SIZE, mVertAttribs2);
820
     int index1 = mVBO1.createImmediatelyFloat(mNumVertices*VERT1_SIZE, mVertAttribs1);
821
     int index2 = mVBO2.createImmediatelyFloat(mNumVertices*VERT2_SIZE, mVertAttribs2);
751 822

  
752 823
     GLES30.glBindBuffer(GLES30.GL_ARRAY_BUFFER, index1 );
753 824
     GLES30.glVertexAttribPointer(program.mAttribute[0], POS_DATA_SIZE, GLES30.GL_FLOAT, false, VERT1_SIZE, OFFSET_POS);
......
767 838
 */
768 839
   public void bindTransformAttribs(DistortedProgram program)
769 840
     {
770
     int index = mTFO.createImmediately(mNumVertices*TRAN_SIZE, null);
841
     int index = mTFO.createImmediatelyFloat(mNumVertices*TRAN_SIZE, null);
771 842

  
772 843
     GLES30.glBindBuffer(GLES30.GL_ARRAY_BUFFER, index );
773 844
     GLES30.glVertexAttribPointer(program.mAttribute[0], POS_DATA_SIZE, GLES30.GL_FLOAT, false, 0, 0);

Also available in: Unified diff