Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'source/blender/blenkernel/intern/subsurf_ccg.c')
-rw-r--r--source/blender/blenkernel/intern/subsurf_ccg.c490
1 files changed, 351 insertions, 139 deletions
diff --git a/source/blender/blenkernel/intern/subsurf_ccg.c b/source/blender/blenkernel/intern/subsurf_ccg.c
index 998bb9835a8..a2c625a7ec3 100644
--- a/source/blender/blenkernel/intern/subsurf_ccg.c
+++ b/source/blender/blenkernel/intern/subsurf_ccg.c
@@ -796,7 +796,7 @@ static void ss_sync_from_derivedmesh(CCGSubSurf *ss,
{
#ifdef WITH_OPENSUBDIV
/* Reset all related descriptors if actual mesh topology changed or if
- * other evlauation-related settings changed.
+ * other evaluation-related settings changed.
*/
if (!ccgSubSurf_needGrids(ss)) {
/* TODO(sergey): Use vertex coordinates and flat subdiv flag. */
@@ -1913,7 +1913,6 @@ static void ccgDM_buffer_copy_normal(
int start = 0;
CCG_key_top_level(&key, ss);
- ccgdm_pbvh_update(ccgdm);
for (i = 0; i < totface; i++) {
CCGFace *f = ccgdm->faceMap[i].face;
@@ -2008,7 +2007,8 @@ static void ccgDM_buffer_copy_triangles(
const int *mat_orig_to_new)
{
GPUBufferMaterial *gpumat, *gpumaterials = dm->drawObject->materials;
- const int totmat = dm->drawObject->totmaterial;
+ const int gpu_totmat = dm->drawObject->totmaterial;
+ const short dm_totmat = dm->totmat;
CCGDerivedMesh *ccgdm = (CCGDerivedMesh *) dm;
CCGSubSurf *ss = ccgdm->ss;
CCGKey key;
@@ -2016,13 +2016,14 @@ static void ccgDM_buffer_copy_triangles(
int gridFaces = gridSize - 1;
DMFlagMat *faceFlags = ccgdm->faceFlags;
int i, totface = ccgSubSurf_getNumFaces(ss);
- int matnr = -1, start;
+ short mat_nr = -1;
+ int start;
int totloops = 0;
- FaceCount *fc = MEM_mallocN(sizeof(*fc) * totmat, "gpumaterial.facecount");
+ FaceCount *fc = MEM_mallocN(sizeof(*fc) * gpu_totmat, "gpumaterial.facecount");
CCG_key_top_level(&key, ss);
- for (i = 0; i < totmat; i++) {
+ for (i = 0; i < gpu_totmat; i++) {
fc[i].i_visible = 0;
fc[i].i_tri_visible = 0;
fc[i].i_hidden = gpumaterials[i].totpolys - 1;
@@ -2037,14 +2038,14 @@ static void ccgDM_buffer_copy_triangles(
int mati;
if (faceFlags) {
- matnr = faceFlags[index].mat_nr;
+ mat_nr = ME_MAT_NR_TEST(faceFlags[index].mat_nr, dm_totmat);
is_hidden = (faceFlags[index].flag & ME_HIDE) != 0;
}
else {
- matnr = 0;
+ mat_nr = 0;
is_hidden = false;
}
- mati = mat_orig_to_new[matnr];
+ mati = mat_orig_to_new[mat_nr];
gpumat = dm->drawObject->materials + mati;
if (is_hidden) {
@@ -2094,7 +2095,7 @@ static void ccgDM_buffer_copy_triangles(
}
/* set the visible polygons */
- for (i = 0; i < totmat; i++) {
+ for (i = 0; i < gpu_totmat; i++) {
gpumaterials[i].totvisiblepolys = fc[i].i_visible;
}
@@ -2116,10 +2117,9 @@ static void ccgDM_buffer_copy_vertex(
int totedge = ccgSubSurf_getNumEdges(ss);
int start = 0;
int edgeSize = ccgSubSurf_getEdgeSize(ss);
-
+
CCG_key_top_level(&key, ss);
- ccgdm_pbvh_update(ccgdm);
-
+
for (i = 0; i < totface; i++) {
CCGFace *f = ccgdm->faceMap[i].face;
int S, x, y, numVerts = ccgSubSurf_getFaceNumVerts(f);
@@ -2167,7 +2167,7 @@ static void ccgDM_buffer_copy_color(
CCGDerivedMesh *ccgdm = (CCGDerivedMesh *) dm;
CCGSubSurf *ss = ccgdm->ss;
CCGKey key;
- const char *mloopcol = user_data;
+ const unsigned char *mloopcol = user_data;
int gridSize = ccgSubSurf_getGridSize(ss);
int gridFaces = gridSize - 1;
int i, totface = ccgSubSurf_getNumFaces(ss);
@@ -2184,10 +2184,10 @@ static void ccgDM_buffer_copy_color(
for (S = 0; S < numVerts; S++) {
for (y = 0; y < gridFaces; y++) {
for (x = 0; x < gridFaces; x++) {
- copy_v3_v3_char((char *)&varray[start + 0], &mloopcol[iface * 16 + 0]);
- copy_v3_v3_char((char *)&varray[start + 3], &mloopcol[iface * 16 + 12]);
- copy_v3_v3_char((char *)&varray[start + 6], &mloopcol[iface * 16 + 8]);
- copy_v3_v3_char((char *)&varray[start + 9], &mloopcol[iface * 16 + 4]);
+ copy_v3_v3_uchar(&varray[start + 0], &mloopcol[iface * 16 + 0]);
+ copy_v3_v3_uchar(&varray[start + 3], &mloopcol[iface * 16 + 12]);
+ copy_v3_v3_uchar(&varray[start + 6], &mloopcol[iface * 16 + 8]);
+ copy_v3_v3_uchar(&varray[start + 9], &mloopcol[iface * 16 + 4]);
start += 12;
iface++;
@@ -2243,7 +2243,7 @@ static void ccgDM_buffer_copy_uv_texpaint(
int i, totface = ccgSubSurf_getNumFaces(ss);
int start = 0;
DMFlagMat *faceFlags = ccgdm->faceFlags;
- int totmaterial = dm->totmat;
+ int dm_totmat = dm->totmat;
MLoopUV **mloopuv_base;
MLoopUV *stencil_base;
int stencil;
@@ -2252,9 +2252,9 @@ static void ccgDM_buffer_copy_uv_texpaint(
/* should have been checked for before, reassert */
BLI_assert(DM_get_loop_data_layer(dm, CD_MLOOPUV));
- mloopuv_base = MEM_mallocN(totmaterial * sizeof(*mloopuv_base), "texslots");
+ mloopuv_base = MEM_mallocN(dm_totmat * sizeof(*mloopuv_base), "texslots");
- for (i = 0; i < totmaterial; i++) {
+ for (i = 0; i < dm_totmat; i++) {
mloopuv_base[i] = DM_paint_uvlayer_active_get(dm, i);
}
@@ -2385,9 +2385,9 @@ static void ccgDM_buffer_copy_edge(
/* part one, handle all normal edges */
for (j = 0; j < totedge; j++) {
CCGFace *f;
- int fhandle;
- int totvert;
- unsigned int S;
+ int fhandle = 0;
+ int totvert = 0;
+ unsigned int S = 0;
CCGEdge *e = ccgdm->edgeMap[j].edge;
bool isloose = !ccgSubSurf_getEdgeNumFaces(e);
@@ -2541,7 +2541,7 @@ static GPUDrawObject *ccgDM_GPUObjectNew(DerivedMesh *dm)
GPUDrawObject *gdo;
DMFlagMat *faceFlags = ccgdm->faceFlags;
int gridFaces = ccgSubSurf_getGridSize(ss) - 1;
- int totmat = (faceFlags) ? dm->totmat : 1;
+ const short dm_totmat = (faceFlags) ? dm->totmat : 1;
GPUBufferMaterial *matinfo;
int i;
unsigned int tot_internal_edges = 0;
@@ -2552,16 +2552,16 @@ static GPUDrawObject *ccgDM_GPUObjectNew(DerivedMesh *dm)
int totface = ccgSubSurf_getNumFaces(ss);
/* object contains at least one material (default included) so zero means uninitialized dm */
- BLI_assert(totmat != 0);
+ BLI_assert(dm_totmat != 0);
- matinfo = MEM_callocN(sizeof(*matinfo) * totmat, "GPU_drawobject_new.mat_orig_to_new");
+ matinfo = MEM_callocN(sizeof(*matinfo) * dm_totmat, "GPU_drawobject_new.mat_orig_to_new");
if (faceFlags) {
for (i = 0; i < totface; i++) {
CCGFace *f = ccgdm->faceMap[i].face;
int numVerts = ccgSubSurf_getFaceNumVerts(f);
int index = GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(f));
- int new_matnr = faceFlags[index].mat_nr;
+ const short new_matnr = ME_MAT_NR_TEST(faceFlags[index].mat_nr, dm_totmat);
matinfo[new_matnr].totelements += numVerts * gridFaces * gridFaces * 6;
matinfo[new_matnr].totloops += numVerts * gridFaces * gridFaces * 4;
matinfo[new_matnr].totpolys++;
@@ -2584,7 +2584,7 @@ static GPUDrawObject *ccgDM_GPUObjectNew(DerivedMesh *dm)
gdo->totvert = 0; /* used to count indices, doesn't really matter for ccgsubsurf */
gdo->totedge = (totedge * edgeSize + tot_internal_edges);
- GPU_buffer_material_finalize(gdo, matinfo, totmat);
+ GPU_buffer_material_finalize(gdo, matinfo, dm_totmat);
/* store total number of points used for triangles */
gdo->tot_triangle_point = ccgSubSurf_getNumFinalFaces(ss) * 6;
@@ -2705,6 +2705,13 @@ static void ccgDM_drawFacesSolid(DerivedMesh *dm, float (*partial_redraw_planes)
GPU_buffers_unbind();
}
+typedef struct {
+ DMVertexAttribs attribs;
+ int numdata;
+
+ GPUAttrib datatypes[GPU_MAX_ATTRIB]; /* TODO, messing up when switching materials many times - [#21056]*/
+} GPUMaterialConv;
+
/* Only used by non-editmesh types */
static void ccgDM_drawMappedFacesGLSL(DerivedMesh *dm,
DMSetMaterial setMaterial,
@@ -2715,14 +2722,15 @@ static void ccgDM_drawMappedFacesGLSL(DerivedMesh *dm,
CCGSubSurf *ss = ccgdm->ss;
CCGKey key;
GPUVertexAttribs gattribs;
- DMVertexAttribs attribs = {{{NULL}}};
- /* MTFace *tf = dm->getTessFaceDataArray(dm, CD_MTFACE); */ /* UNUSED */
+ int a, b, do_draw, new_matnr;
+ DMFlagMat *faceFlags = ccgdm->faceFlags;
+ unsigned char *varray;
+ size_t max_element_size = 0;
+ int tot_loops = 0;
+ int totpoly = ccgSubSurf_getNumFaces(ss);
int gridSize = ccgSubSurf_getGridSize(ss);
int gridFaces = gridSize - 1;
int edgeSize = ccgSubSurf_getEdgeSize(ss);
- DMFlagMat *faceFlags = ccgdm->faceFlags;
- const float (*lnors)[3] = dm->getLoopDataArray(dm, CD_NORMAL);
- int a, i, do_draw, numVerts, matnr, new_matnr, totface;
#ifdef WITH_OPENSUBDIV
if (ccgdm->useGpuBackend) {
@@ -2791,154 +2799,358 @@ static void ccgDM_drawMappedFacesGLSL(DerivedMesh *dm,
}
#endif
+ glShadeModel(GL_SMOOTH);
+
CCG_key_top_level(&key, ss);
ccgdm_pbvh_update(ccgdm);
- do_draw = 0;
- matnr = -1;
+ /* workaround for NVIDIA GPUs on Mac not supporting vertex arrays + interleaved formats, see T43342 */
+ if ((GPU_type_matches(GPU_DEVICE_NVIDIA, GPU_OS_MAC, GPU_DRIVER_ANY) && (U.gameflags & USER_DISABLE_VBO)) ||
+ setDrawOptions != NULL)
+ {
+ const float (*lnors)[3] = dm->getLoopDataArray(dm, CD_NORMAL);
+ DMVertexAttribs attribs = {{{NULL}}};
+ int i;
+ int matnr = -1;
+ do_draw = 0;
#define PASSATTRIB(dx, dy, vert) { \
if (attribs.totorco) \
index = getFaceIndex(ss, f, S, x + dx, y + dy, edgeSize, gridSize); \
else \
index = 0; \
- DM_draw_attrib_vertex(&attribs, a, index, vert, ((a) * 4) + vert); \
+ DM_draw_attrib_vertex(&attribs, a, index, vert, ((a) * 4) + vert); \
} (void)0
- totface = ccgSubSurf_getNumFaces(ss);
- for (a = 0, i = 0; i < totface; i++) {
- CCGFace *f = ccgdm->faceMap[i].face;
- const float (*ln)[3] = NULL;
- int S, x, y, drawSmooth;
- int index = GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(f));
- int origIndex = ccgDM_getFaceMapIndex(ss, f);
-
- numVerts = ccgSubSurf_getFaceNumVerts(f);
-
- if (faceFlags) {
- drawSmooth = (lnors || (faceFlags[index].flag & ME_SMOOTH));
- new_matnr = faceFlags[index].mat_nr + 1;
- }
- else {
- drawSmooth = 1;
- new_matnr = 1;
- }
-
- if (lnors) {
- ln = lnors;
- lnors += (gridFaces * gridFaces * numVerts) * 4;
- }
+ totpoly = ccgSubSurf_getNumFaces(ss);
+ for (a = 0, i = 0; i < totpoly; i++) {
+ CCGFace *f = ccgdm->faceMap[i].face;
+ const float (*ln)[3] = NULL;
+ int S, x, y, drawSmooth;
+ int index = GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(f));
+ int origIndex = ccgDM_getFaceMapIndex(ss, f);
- if (new_matnr != matnr) {
- do_draw = setMaterial(matnr = new_matnr, &gattribs);
- if (do_draw)
- DM_vertex_attributes_from_gpu(dm, &gattribs, &attribs);
- }
+ int numVerts = ccgSubSurf_getFaceNumVerts(f);
- if (!do_draw || (setDrawOptions && (origIndex != ORIGINDEX_NONE) &&
- (setDrawOptions(userData, origIndex) == DM_DRAW_OPTION_SKIP)))
- {
- a += gridFaces * gridFaces * numVerts;
- continue;
- }
+ if (faceFlags) {
+ drawSmooth = (lnors || (faceFlags[index].flag & ME_SMOOTH));
+ new_matnr = faceFlags[index].mat_nr + 1;
+ }
+ else {
+ drawSmooth = 1;
+ new_matnr = 1;
+ }
- glShadeModel(drawSmooth ? GL_SMOOTH : GL_FLAT);
- for (S = 0; S < numVerts; S++) {
- CCGElem *faceGridData = ccgSubSurf_getFaceGridDataArray(ss, f, S);
- CCGElem *vda, *vdb;
+ if (lnors) {
+ ln = lnors;
+ lnors += (gridFaces * gridFaces * numVerts) * 4;
+ }
- if (ln) {
- glBegin(GL_QUADS);
- for (y = 0; y < gridFaces; y++) {
- for (x = 0; x < gridFaces; x++) {
- float *aco = CCG_grid_elem_co(&key, faceGridData, x, y);
- float *bco = CCG_grid_elem_co(&key, faceGridData, x + 1, y);
- float *cco = CCG_grid_elem_co(&key, faceGridData, x + 1, y + 1);
- float *dco = CCG_grid_elem_co(&key, faceGridData, x, y + 1);
+ if (new_matnr != matnr) {
+ do_draw = setMaterial(matnr = new_matnr, &gattribs);
+ if (do_draw)
+ DM_vertex_attributes_from_gpu(dm, &gattribs, &attribs);
+ }
- PASSATTRIB(0, 1, 1);
- glNormal3fv(ln[1]);
- glVertex3fv(dco);
- PASSATTRIB(1, 1, 2);
- glNormal3fv(ln[2]);
- glVertex3fv(cco);
- PASSATTRIB(1, 0, 3);
- glNormal3fv(ln[3]);
- glVertex3fv(bco);
- PASSATTRIB(0, 0, 0);
- glNormal3fv(ln[0]);
- glVertex3fv(aco);
+ if (!do_draw || (setDrawOptions && (origIndex != ORIGINDEX_NONE) &&
+ (setDrawOptions(userData, origIndex) == DM_DRAW_OPTION_SKIP)))
+ {
+ a += gridFaces * gridFaces * numVerts;
+ continue;
+ }
- ln += 4;
- a++;
+ glShadeModel(drawSmooth ? GL_SMOOTH : GL_FLAT);
+ for (S = 0; S < numVerts; S++) {
+ CCGElem *faceGridData = ccgSubSurf_getFaceGridDataArray(ss, f, S);
+ CCGElem *vda, *vdb;
+
+ if (ln) {
+ glBegin(GL_QUADS);
+ for (y = 0; y < gridFaces; y++) {
+ for (x = 0; x < gridFaces; x++) {
+ float *aco = CCG_grid_elem_co(&key, faceGridData, x, y);
+ float *bco = CCG_grid_elem_co(&key, faceGridData, x + 1, y);
+ float *cco = CCG_grid_elem_co(&key, faceGridData, x + 1, y + 1);
+ float *dco = CCG_grid_elem_co(&key, faceGridData, x, y + 1);
+
+ PASSATTRIB(0, 1, 1);
+ glNormal3fv(ln[1]);
+ glVertex3fv(dco);
+ PASSATTRIB(1, 1, 2);
+ glNormal3fv(ln[2]);
+ glVertex3fv(cco);
+ PASSATTRIB(1, 0, 3);
+ glNormal3fv(ln[3]);
+ glVertex3fv(bco);
+ PASSATTRIB(0, 0, 0);
+ glNormal3fv(ln[0]);
+ glVertex3fv(aco);
+
+ ln += 4;
+ a++;
+ }
}
+ glEnd();
}
- glEnd();
- }
- else if (drawSmooth) {
- for (y = 0; y < gridFaces; y++) {
- glBegin(GL_QUAD_STRIP);
- for (x = 0; x < gridFaces; x++) {
+ else if (drawSmooth) {
+ for (y = 0; y < gridFaces; y++) {
+ glBegin(GL_QUAD_STRIP);
+ for (x = 0; x < gridFaces; x++) {
+ vda = CCG_grid_elem(&key, faceGridData, x, y + 0);
+ vdb = CCG_grid_elem(&key, faceGridData, x, y + 1);
+
+ PASSATTRIB(0, 0, 0);
+ glNormal3fv(CCG_elem_no(&key, vda));
+ glVertex3fv(CCG_elem_co(&key, vda));
+
+ PASSATTRIB(0, 1, 1);
+ glNormal3fv(CCG_elem_no(&key, vdb));
+ glVertex3fv(CCG_elem_co(&key, vdb));
+
+ if (x != gridFaces - 1)
+ a++;
+ }
+
vda = CCG_grid_elem(&key, faceGridData, x, y + 0);
vdb = CCG_grid_elem(&key, faceGridData, x, y + 1);
-
- PASSATTRIB(0, 0, 0);
+
+ PASSATTRIB(0, 0, 3);
glNormal3fv(CCG_elem_no(&key, vda));
glVertex3fv(CCG_elem_co(&key, vda));
- PASSATTRIB(0, 1, 1);
+ PASSATTRIB(0, 1, 2);
glNormal3fv(CCG_elem_no(&key, vdb));
glVertex3fv(CCG_elem_co(&key, vdb));
- if (x != gridFaces - 1)
+ glEnd();
+
+ a++;
+ }
+ }
+ else {
+ glBegin(GL_QUADS);
+ for (y = 0; y < gridFaces; y++) {
+ for (x = 0; x < gridFaces; x++) {
+ float *aco = CCG_grid_elem_co(&key, faceGridData, x, y);
+ float *bco = CCG_grid_elem_co(&key, faceGridData, x + 1, y);
+ float *cco = CCG_grid_elem_co(&key, faceGridData, x + 1, y + 1);
+ float *dco = CCG_grid_elem_co(&key, faceGridData, x, y + 1);
+
+ ccgDM_glNormalFast(aco, bco, cco, dco);
+
+ PASSATTRIB(0, 1, 1);
+ glVertex3fv(dco);
+ PASSATTRIB(1, 1, 2);
+ glVertex3fv(cco);
+ PASSATTRIB(1, 0, 3);
+ glVertex3fv(bco);
+ PASSATTRIB(0, 0, 0);
+ glVertex3fv(aco);
+
a++;
+ }
}
+ glEnd();
+ }
+ }
+ }
- vda = CCG_grid_elem(&key, faceGridData, x, y + 0);
- vdb = CCG_grid_elem(&key, faceGridData, x, y + 1);
+#undef PASSATTRIB
+ }
+ else {
+ GPUMaterialConv *matconv;
+ size_t offset;
+ int *mat_orig_to_new;
+ int tot_active_mat;
+ GPUBuffer *buffer = NULL;
- PASSATTRIB(0, 0, 3);
- glNormal3fv(CCG_elem_no(&key, vda));
- glVertex3fv(CCG_elem_co(&key, vda));
+ GPU_vertex_setup(dm);
+ GPU_normal_setup(dm);
+ GPU_triangle_setup(dm);
- PASSATTRIB(0, 1, 2);
- glNormal3fv(CCG_elem_no(&key, vdb));
- glVertex3fv(CCG_elem_co(&key, vdb));
+ tot_active_mat = dm->drawObject->totmaterial;
- glEnd();
+ matconv = MEM_callocN(sizeof(*matconv) * tot_active_mat,
+ "cdDM_drawMappedFacesGLSL.matconv");
+ mat_orig_to_new = MEM_mallocN(sizeof(*mat_orig_to_new) * dm->totmat,
+ "cdDM_drawMappedFacesGLSL.mat_orig_to_new");
- a++;
+ /* part one, check what attributes are needed per material */
+ for (a = 0; a < tot_active_mat; a++) {
+ new_matnr = dm->drawObject->materials[a].mat_nr;
+
+ /* map from original material index to new
+ * GPUBufferMaterial index */
+ mat_orig_to_new[new_matnr] = a;
+ do_draw = setMaterial(new_matnr + 1, &gattribs);
+
+ if (do_draw) {
+ int numdata = 0;
+ DM_vertex_attributes_from_gpu(dm, &gattribs, &matconv[a].attribs);
+
+ if (matconv[a].attribs.totorco && matconv[a].attribs.orco.array) {
+ matconv[a].datatypes[numdata].index = matconv[a].attribs.orco.gl_index;
+ matconv[a].datatypes[numdata].size = 3;
+ matconv[a].datatypes[numdata].type = GL_FLOAT;
+ numdata++;
+ }
+ for (b = 0; b < matconv[a].attribs.tottface; b++) {
+ if (matconv[a].attribs.tface[b].array) {
+ matconv[a].datatypes[numdata].index = matconv[a].attribs.tface[b].gl_index;
+ matconv[a].datatypes[numdata].size = 2;
+ matconv[a].datatypes[numdata].type = GL_FLOAT;
+ numdata++;
+ }
+ }
+ for (b = 0; b < matconv[a].attribs.totmcol; b++) {
+ if (matconv[a].attribs.mcol[b].array) {
+ matconv[a].datatypes[numdata].index = matconv[a].attribs.mcol[b].gl_index;
+ matconv[a].datatypes[numdata].size = 4;
+ matconv[a].datatypes[numdata].type = GL_UNSIGNED_BYTE;
+ numdata++;
+ }
+ }
+ if (matconv[a].attribs.tottang && matconv[a].attribs.tang.array) {
+ matconv[a].datatypes[numdata].index = matconv[a].attribs.tang.gl_index;
+ matconv[a].datatypes[numdata].size = 4;
+ matconv[a].datatypes[numdata].type = GL_FLOAT;
+ numdata++;
+ }
+ if (numdata != 0) {
+ matconv[a].numdata = numdata;
+ max_element_size = max_ii(GPU_attrib_element_size(matconv[a].datatypes, numdata), max_element_size);
}
}
- else {
- glBegin(GL_QUADS);
- for (y = 0; y < gridFaces; y++) {
- for (x = 0; x < gridFaces; x++) {
- float *aco = CCG_grid_elem_co(&key, faceGridData, x, y);
- float *bco = CCG_grid_elem_co(&key, faceGridData, x + 1, y);
- float *cco = CCG_grid_elem_co(&key, faceGridData, x + 1, y + 1);
- float *dco = CCG_grid_elem_co(&key, faceGridData, x, y + 1);
+ }
- ccgDM_glNormalFast(aco, bco, cco, dco);
+ /* part two, generate and fill the arrays with the data */
+ if (max_element_size > 0) {
+ buffer = GPU_buffer_alloc(max_element_size * dm->drawObject->tot_loop_verts, false);
- PASSATTRIB(0, 1, 1);
- glVertex3fv(dco);
- PASSATTRIB(1, 1, 2);
- glVertex3fv(cco);
- PASSATTRIB(1, 0, 3);
- glVertex3fv(bco);
- PASSATTRIB(0, 0, 0);
- glVertex3fv(aco);
-
- a++;
+ if (buffer == NULL) {
+ buffer = GPU_buffer_alloc(max_element_size * dm->drawObject->tot_loop_verts, true);
+ }
+ varray = GPU_buffer_lock_stream(buffer, GPU_BINDING_ARRAY);
+ if (varray == NULL) {
+ GPU_buffers_unbind();
+ GPU_buffer_free(buffer);
+ MEM_freeN(mat_orig_to_new);
+ MEM_freeN(matconv);
+ fprintf(stderr, "Out of memory, can't draw object\n");
+ return;
+ }
+
+ for (a = 0; a < totpoly; a++) {
+ CCGFace *f = ccgdm->faceMap[a].face;
+ int index = GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(f));
+ int S, x, y, numVerts = ccgSubSurf_getFaceNumVerts(f);
+ int i;
+
+ if (faceFlags) {
+ i = mat_orig_to_new[faceFlags[index].mat_nr];
+ }
+ else {
+ i = mat_orig_to_new[0];
+ }
+
+ if (matconv[i].numdata != 0) {
+ for (S = 0; S < numVerts; S++) {
+ for (y = 0; y < gridFaces; y++) {
+ for (x = 0; x < gridFaces; x++) {
+
+ offset = tot_loops * max_element_size;
+
+ if (matconv[i].attribs.totorco && matconv[i].attribs.orco.array) {
+ int index;
+
+ index = getFaceIndex(ss, f, S, x, y, edgeSize, gridSize);
+ copy_v3_v3((float *)&varray[offset],
+ (float *)matconv[i].attribs.orco.array[index]);
+ index = getFaceIndex(ss, f, S, x + 1, y, edgeSize, gridSize);
+ copy_v3_v3((float *)&varray[offset + max_element_size],
+ (float *)matconv[i].attribs.orco.array[index]);
+ index = getFaceIndex(ss, f, S, x + 1, y + 1, edgeSize, gridSize);
+ copy_v3_v3((float *)&varray[offset + 2 * max_element_size],
+ (float *)matconv[i].attribs.orco.array[index]);
+ index = getFaceIndex(ss, f, S, x, y + 1, edgeSize, gridSize);
+ copy_v3_v3((float *)&varray[offset + 3 * max_element_size],
+ (float *)matconv[i].attribs.orco.array[index]);
+
+ offset += sizeof(float) * 3;
+ }
+ for (b = 0; b < matconv[i].attribs.tottface; b++) {
+ if (matconv[i].attribs.tface[b].array) {
+ const MLoopUV *mloopuv = matconv[i].attribs.tface[b].array + tot_loops;
+
+ copy_v2_v2((float *)&varray[offset], mloopuv[0].uv);
+ copy_v2_v2((float *)&varray[offset + max_element_size], mloopuv[3].uv);
+ copy_v2_v2((float *)&varray[offset + 2 * max_element_size], mloopuv[2].uv);
+ copy_v2_v2((float *)&varray[offset + 3 * max_element_size], mloopuv[1].uv);
+
+ offset += sizeof(float) * 2;
+ }
+ }
+ for (b = 0; b < matconv[i].attribs.totmcol; b++) {
+ if (matconv[i].attribs.mcol[b].array) {
+ const MLoopCol *mloopcol = matconv[i].attribs.mcol[b].array + tot_loops;
+
+ copy_v4_v4_uchar(&varray[offset], &mloopcol[0].r);
+ copy_v4_v4_uchar(&varray[offset + max_element_size], &mloopcol[3].r);
+ copy_v4_v4_uchar(&varray[offset + 2 * max_element_size], &mloopcol[2].r);
+ copy_v4_v4_uchar(&varray[offset + 3 * max_element_size], &mloopcol[1].r);
+
+ offset += sizeof(unsigned char) * 4;
+ }
+ }
+ if (matconv[i].attribs.tottang && matconv[i].attribs.tang.array) {
+ const float (*looptang)[4] = (const float (*)[4])matconv[i].attribs.tang.array + tot_loops;
+
+ copy_v4_v4((float *)&varray[offset], looptang[0]);
+ copy_v4_v4((float *)&varray[offset + max_element_size], looptang[3]);
+ copy_v4_v4((float *)&varray[offset + 2 * max_element_size], looptang[2]);
+ copy_v4_v4((float *)&varray[offset + 3 * max_element_size], looptang[1]);
+
+ offset += sizeof(float) * 4;
+ }
+
+ tot_loops += 4;
+ }
+ }
}
}
- glEnd();
+ else {
+ tot_loops += 4 * numVerts * gridFaces * gridFaces;
+ }
}
+ GPU_buffer_unlock(buffer, GPU_BINDING_ARRAY);
}
+
+ for (a = 0; a < tot_active_mat; a++) {
+ new_matnr = dm->drawObject->materials[a].mat_nr;
+
+ do_draw = setMaterial(new_matnr + 1, &gattribs);
+
+ if (do_draw) {
+ if (matconv[a].numdata) {
+ GPU_interleaved_attrib_setup(buffer, matconv[a].datatypes, matconv[a].numdata, max_element_size);
+ }
+ GPU_buffer_draw_elements(dm->drawObject->triangles, GL_TRIANGLES,
+ dm->drawObject->materials[a].start, dm->drawObject->materials[a].totelements);
+ if (matconv[a].numdata) {
+ GPU_interleaved_attrib_unbind();
+ }
+ }
+ }
+
+ GPU_buffers_unbind();
+ if (buffer)
+ GPU_buffer_free(buffer);
+
+ MEM_freeN(mat_orig_to_new);
+ MEM_freeN(matconv);
}
-#undef PASSATTRIB
+ glShadeModel(GL_FLAT);
}
static void ccgDM_drawFacesGLSL(DerivedMesh *dm, DMSetMaterial setMaterial)
@@ -4805,7 +5017,7 @@ struct DerivedMesh *subsurf_make_derived_from_derived(
*
* TODO(sergey): There was a good eason why final calculation
* used to free entirely cached subsurf structure. reason of
- * this is to be investiated still to be sure we don't have
+ * this is to be investigated still to be sure we don't have
* regressions here.
*/
if (use_gpu_backend) {