/** * @brief pass * @param img * @param S * @return */ bool pass(Image *img, int S) { float Sf = float(S); float Sf2 = Sf * Sf; for(int i = 0; i < nSuperPixels; i++) { prevX[i] = centers[i].x; prevY[i] = centers[i].y; } //for each cluster for(int i = 0; i < nSuperPixels; i++) { float i_f = float(i); //Search in Sx2 radius for(int j = -S; j < S; j++) { int vY = centers[i].y + j; for(int k = -S; k < S; k++) { int vX = centers[i].x + k; float *pixel = (*img)(vX, vY); float *l_d = (*labels_distance)(vX, vY); float dS = float(distanceS(vX, vY, centers[i].x, centers[i].y)) / Sf2; float dC = distanceC(pixel, centers[i].value, img->channels) / mPixel[i]; float D = dC + dS; if(D < l_d[1]) { l_d[0] = i_f; l_d[1] = D; l_d[2] = dC; } } } } //update mPixel for(int i = 0; i < labels_distance->size(); i += labels_distance->channels) { int label = int(labels_distance->data[i]); if(label < 0) { continue; } if(mPixel[label] < labels_distance->data[i + 2]) { mPixel[label] = labels_distance->data[i + 2]; } } //update clusters for(int i = 0; i < nSuperPixels; i++) { centers[i].x = 0; centers[i].y = 0; counter[i] = 0; int ind = i * img->channels; for(int j = 0; j < img->channels; j++) { col_values[ind + j] = 0.0f; } } for(int j = 0; j < img->height; j++) { for(int k = 0; k < img->width; k++) { float *l_d = (*labels_distance)(k, j); int label = int(l_d[0]); if(label > -1) { centers[label].x += k; centers[label].y += j; counter[label]++; int ind = label * img->channels; float *col = (*img)(k, j); for(int p = 0; p < img->channels; p++) { col_values[ind + p] += col[p]; } } } } float E = 0.0f; for(int i = 0; i < nSuperPixels; i++) { if(counter[i] <= 0) { continue; } centers[i].x /= counter[i]; centers[i].y /= counter[i]; int ind = i * img->channels; for(int j = 0; j < img->channels; j++) { centers[i].value[j] = col_values[ind + j] / float(counter[i]); } //Error int tx = prevX[i] - centers[i].x; int ty = prevY[i] - centers[i].y; float tmpErr = sqrtf(float(tx * tx + ty * ty)); E += tmpErr; } return (E > (0.0001f * float(nSuperPixels))); }
void smoothingLineCGM(surface_mesh *pm, int *vert, double *pT, double *pU, double *pV, int iSurf, int iV_U, int n, CGMedge edge) { int i, j=0, jj; double t, tp, tn, tu, tv, sp, sn; double x, y, z, x0, y0, z0, x1, y1, z1, x2, y2, z2; double du, k=0.0, k0, k1, fi0_, fi1_, f1, p; int v, vp, vn; double xyz[3]; while (j < 5) { for (i=n-2; i>0; i--) { v = vert[i]; vp = vert[i-1]; tp = pT[i-1]; vn = vert[i+1]; tn = pT[i+1]; if (tp > tn) { t = tp; tp = tn; tn = t; } x1 = pm->vert[vp].x; y1 = pm->vert[vp].y; z1 = pm->vert[vp].z; x2 = pm->vert[vn].x; y2 = pm->vert[vn].y; z2 = pm->vert[vn].z; sp = sizeFace(pm, 0.5*(pm->vert[v].x+x1), 0.5*(pm->vert[v].y+y1), 0.5*(pm->vert[v].z+z1)); sn = sizeFace(pm, 0.5*(pm->vert[v].x+x2), 0.5*(pm->vert[v].y+y2), 0.5*(pm->vert[v].z+z2)); /* find point on surface */ t = pT[i]; if (iSurf>=0) { bounLine(pm, iV_U, t, &tu, &tv); bounSurf(pm, iSurf, tu, tv, &x, &y, &z); } else { CGM_GetEdgeCoordsFromU(edge, t, xyz); x = xyz[0]; y = xyz[1]; z = xyz[2]; } f1 = (sp/sn - distance(x1, y1, z1, x, y, z)/distance(x2, y2, z2, x, y, z))* (sp/sn - distance(x1, y1, z1, x, y, z)/distance(x2, y2, z2, x, y, z)); for (jj=0; jj<222; jj++) { /* NEW METH */ if (f1 < 0.01) break; du = 0.2; /*???*/ do { du /= 2.0; if (iSurf>=0) { bounLine(pm, iV_U, t+du, &tu, &tv); bounSurf(pm, iSurf, tu, tv, &x0, &y0, &z0); } else { CGM_GetEdgeCoordsFromU(edge, t+du, xyz); x0 = xyz[0]; y0 = xyz[1]; z0 = xyz[2]; } p = distanceS(x, y, z, x0, y0, z0); } while (p > 0.1*sp*sn); k0 = -0.9; k1 = 1.0; if (du == 0.0) errorExit3(3, "du == 0.0 "); if (t + k0*du < tp) k0 = (tp-t)/du; if (t + k1*du > tn) k1 = (tn-t)/du; while (k1 - k0 > 0.00001) {/*min of funk*/ k = 0.5*(k0+k1); if (iSurf>=0) { bounLine(pm, iV_U, t+k*du, &tu, &tv); bounSurf(pm, iSurf, tu, tv, &x, &y, &z); } else { CGM_GetEdgeCoordsFromU(edge, t+k*du, xyz); x = xyz[0]; y = xyz[1]; z = xyz[2]; } fi0_ = (sp/sn - distance(x1, y1, z1, x, y, z)/distance(x2, y2, z2, x, y, z))* (sp/sn - distance(x1, y1, z1, x, y, z)/distance(x2, y2, z2, x, y, z)); if (iSurf>=0) { bounLine(pm, iV_U, t+(k+fabs(k)*0.01)*du, &tu, &tv); bounSurf(pm, iSurf, tu, tv, &x, &y, &z); } else { CGM_GetEdgeCoordsFromU(edge, t+(k+fabs(k)*0.01)*du, xyz); x = xyz[0]; y = xyz[1]; z = xyz[2]; } fi1_ = (sp/sn - distance(x1, y1, z1, x, y, z)/distance(x2, y2, z2, x, y, z))* (sp/sn - distance(x1, y1, z1, x, y, z)/distance(x2, y2, z2, x, y, z)); if (fi1_ - fi0_ > 0.) k1 = k; else k0 = k; } t += k*du; if (iSurf>=0) { bounLine(pm, iV_U, t, &tu, &tv); bounSurf(pm, iSurf, tu, tv, &x, &y, &z); } else { CGM_GetEdgeCoordsFromU(edge, t, xyz); x = xyz[0]; y = xyz[1]; z = xyz[2]; } f1 = (sp/sn - distance(x1, y1, z1, x, y, z)/distance(x2, y2, z2, x, y, z))* (sp/sn - distance(x1, y1, z1, x, y, z)/distance(x2, y2, z2, x, y, z)); } /*NEW METH*/ if (iSurf>=0) { bounLine(pm, iV_U, t, &tu, &tv); bounSurf(pm, iSurf, tu, tv, &x, &y, &z); pU[i] = tu, pV[i] = tv; } else { CGM_GetEdgeCoordsFromU(edge, t, xyz); x = xyz[0]; y = xyz[1]; z = xyz[2]; } pT[i] = t; pm->vert[v].x = x; pm->vert[v].y = y; pm->vert[v].z = z; } j++; } return; }