//-------------------------------------------------------------- void Projection::updateBoundaries () { // Extrémités de la zone double x0,y0, x1,y1; screen2map(-1, -1, &x0, &y0); screen2map(W+1, H+1, &x1, &y1); xmin = x0; xmax = x1; if (y0 < y1) { double a = y1; y1 = y0; y0 = a; } ymin = y1; ymax = y0; //printf("Projection::updateBoundaries X(%f %f) Y(%f %f)\n", xmin,xmax, ymin,ymax); if (W*H != 0) coefremp = 10000.0*fabs( ((xmax-xmin)*(ymax-ymin)) / (W*H) ); else coefremp = 10000.0; emit projectionUpdated(); }
//-------------------------------------------------------------- void Projection::setMapPointInScreen (double x,double y, int pi,int pj) { while (x > 180.0) { x -= 360.0; } while (x < -180.0) { x += 360.0; } //printf("setMapPointInScreen x=%f y=%f pi=%d pj=%d\n", x,y, pi,pj); // Recherche dichotomique de la valeur de CX,CY pour que le pt (x,y) soit près de (pi,pj) // ie. screen2map(i,j) = (x,y) int n; double xx, yy; double vmin, vtest, vmax; // Cherche CY vmin = -360; vmax = 360; n = 0; CX = x; // valeur provisoire do { n ++; vtest = (vmin+vmax)/2.0; CY = vtest; screen2map(pi,pj, &xx,&yy); if (y < yy) vmax = vtest; else vmin = vtest; //printf("Y %3d : y=%f yy=%f CY=%f\n", n, y,yy, CY); } while (n<30 && fabs(yy-y)>1e-4); // Cherche CX vmin = -360; vmax = 360; n = 0; do { n ++; vtest = (vmin+vmax)/2.0; CX = vtest; screen2map(pi,pj, &xx,&yy); if (x < xx) vmax = vtest; else vmin = vtest; //printf("X %3d : x=%f xx=%f \n", n, x,xx); } while (n<30 && fabs(xx-x)>1e-4); updateBoundaries(); }
//-------------------------------------------------------------- void Projection::setCentralPixel (int pi, int pj) { double x, y; screen2map(pi, pj, &x, &y); setMapPointInScreen(x, y, W/2, H/2); }
//-------------------------------------------------------------- void Projection::move (double dx, double dy) { double px,py; screen2map(W/2,H/2, &px,&py); setMapPointInScreen(px, py, (int)(W/2+dx*W+0.5), (int)(H/2-dy*H+0.5)); }
//-------------------------------------------------------------- void Projection_libproj::setVisibleArea(double x0, double y0, double x1, double y1) { //printf("setVisibleArea X(%f %f) Y(%f %f)\n", x0, x1,y0,y1); if (x1 == x0) { x1 = x0+0.1; } if (y1 == y0) { y1 = y0+0.1; } if (x0 > x1) { double a = x1; x1 = x0; x0 = a; } if (y0 > y1) { double a = y1; y1 = y0; y0 = a; } while (x0 > 360) { x0 -= 360; x1 -= 360; } while (x0 < -360) { x0 += 360; x1 += 360; } while (y0 <= -98) { y0 += 10; y1 += 10; } while (y1 >= 98) { y0 -= 10; y1 -= 10; } if (x0 > 180. && x1 > 180.) { // in this case screen2map returns -180 .. 0 x0 -= 360.; x1 -= 360.; } double sx, sy; // On cherche l'échelle qui permet d'englober la zone // En commençant par placer le coin haut gauche (x0,y1) de la zone int n; double dsc, smin, stest, smax, xx,yy; sx = sy = scale; // Vertical scale stest = 0; smin = 0.01; smax = scalemax; n = 0; do { dsc = stest; stest = (smin+smax)/2.0; dsc = fabs(dsc-stest); setScale(stest); setMapPointInScreen(x0,y1, 0,0); screen2map(W, H, &xx,&yy); if (yy < y0) smin = stest; else smax = stest; //printf("Y %3d smin=%f smax=%f %f -> %f\n", n,smin,smax, y1,yy); n ++; } while (n<30 && dsc>1e-4); sy = stest; // Horizontal scale stest = 0; smin = 0.01; smax = scalemax; n = 0; do { dsc = stest; stest = (smin+smax)/2.0; dsc = fabs(dsc-stest); setScale(stest); setMapPointInScreen(x0,y1, 0,0); screen2map(W, H, &xx,&yy); if (xx > x1) smin = stest; else smax = stest; //printf("X %3d stest=%f %f -> %f\n", n,stest, x1,xx); n ++; } while (n<30 && dsc>1e-4); sx = stest; if (sx < sy) { setScale(sx); setMapPointInScreen(x0, (y0+y1)/2, 0,H/2); //printf("1\n"); } else { //printf("2\n"); setScale(sy); setMapPointInScreen( (x0+x1)/2, y0, W/2,H); } }