00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015 #include <stdio.h>
00016 #include <math.h>
00017 #include <string.h>
00018 #include "math_graphics.h"
00019 #include "Axes.h"
00020
00021 #include "GetProperty.h"
00022 #include "SetProperty.h"
00023 #include "BuildObjects.h"
00024 #include "DrawObjects.h"
00025 #include "Xcall1.h"
00026 #include "MALLOC.h"
00027 #include "sciprint.h"
00028 #include "clipping.h"
00029 #include "CurrentObjectsManagement.h"
00030
00031
00032
00033 static void PaintTriangle __PARAMS((double sx[], double sy[], double fxy[],
00034 int zxy[],
00035 double zlevel[], int fill[], BOOL with_mesh));
00036 static void PermutOfSort __PARAMS((int tab[], int perm[]));
00037 static void FindIntersection __PARAMS((double sx[], double sy[], double fxy[],
00038 double z, int inda, int indb,
00039 integer *xint, integer *yint));
00040 void newfec __PARAMS((integer *xm,integer *ym,double *triangles,double *func,integer *Nnode,
00041 integer *Ntr,double *zminmax,integer *colminmax, integer *colout, BOOL with_mesh));
00042 extern void initsubwin();
00043
00044 extern void compute_data_bounds2(int cflag,char dataflag,char *logflags,double *x,double *y,int n1,int n2,double *drect);
00045 extern BOOL update_specification_bounds(sciPointObj *psubwin, double *rect,int flag);
00046 extern int re_index_brect(double * brect, double * drect);
00047 extern BOOL strflag2axes_properties(sciPointObj * psubwin, char * strflag);
00048 extern int CreatePrettyGradsFromNax(sciPointObj * psubwin,int * Nax);
00049
00050 void get_frame_in_pixel(integer WIRect[]);
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075 int C2F(fec)(double *x, double *y, double *triangles, double *func, integer *Nnode, integer *Ntr,
00076 char *strflag, char *legend, double *brect, integer *aaint, double *zminmax,
00077 integer *colminmax, integer *colout, BOOL with_mesh, BOOL flagNax, integer lstr1, integer lstr2)
00078 {
00079 integer n1=1;
00080
00081
00082
00083
00084 long hdltab[2];
00085 int cmpt=0,styl[2];
00086 sciPointObj *pptabofpointobj;
00087 sciPointObj *psubwin;
00088 double drect[6];
00089
00090 BOOL bounds_changed = FALSE;
00091 BOOL axes_properties_changed = FALSE;
00092
00093
00094 psubwin = sciGetCurrentSubWin();
00095
00096 checkRedrawing() ;
00097
00098
00099
00100
00101 if (sciGetSurface(psubwin) == (sciPointObj *) NULL)
00102 {
00103 pSUBWIN_FEATURE (psubwin)->is3d = FALSE;
00104 pSUBWIN_FEATURE (psubwin)->project[2]= 0;
00105 }
00106 else
00107 {
00108 pSUBWIN_FEATURE (psubwin)->theta_kp=pSUBWIN_FEATURE (psubwin)->theta;
00109 pSUBWIN_FEATURE (psubwin)->alpha_kp=pSUBWIN_FEATURE (psubwin)->alpha;
00110 }
00111
00112 pSUBWIN_FEATURE (psubwin)->alpha = 0.0;
00113 pSUBWIN_FEATURE (psubwin)->theta = 270.0;
00114
00115
00116
00117
00118
00119 sciSetIsClipping (psubwin,0);
00120
00121
00122
00123
00124 if (sciGetGraphicMode (psubwin)->autoscaling) {
00125
00126 switch (strflag[1]) {
00127 case '0':
00128
00129 break;
00130 case '1' : case '3' : case '5' : case '7':
00131
00132 re_index_brect(brect, drect);
00133 break;
00134 case '2' : case '4' : case '6' : case '8':case '9':
00135
00136
00137 compute_data_bounds2(0,'g',pSUBWIN_FEATURE(psubwin)->logflags,x,y,n1,*Nnode,drect);
00138 break;
00139 }
00140 if (!pSUBWIN_FEATURE(psubwin)->FirstPlot &&
00141 (strflag[1] == '7' || strflag[1] == '8' || strflag[1] == '9')) {
00142 drect[0] = Min(pSUBWIN_FEATURE(psubwin)->SRect[0],drect[0]);
00143 drect[2] = Min(pSUBWIN_FEATURE(psubwin)->SRect[2],drect[2]);
00144 drect[1] = Max(pSUBWIN_FEATURE(psubwin)->SRect[1],drect[1]);
00145 drect[3] = Max(pSUBWIN_FEATURE(psubwin)->SRect[3],drect[3]);
00146 }
00147 if (strflag[1] != '0')
00148 bounds_changed = update_specification_bounds(psubwin, drect,2);
00149 }
00150
00151 if(pSUBWIN_FEATURE (psubwin)->FirstPlot == TRUE) bounds_changed = TRUE;
00152
00153 axes_properties_changed = strflag2axes_properties(psubwin, strflag);
00154
00155 pSUBWIN_FEATURE (psubwin)->FirstPlot = FALSE;
00156
00157
00158
00159
00160 pSUBWIN_FEATURE(psubwin)->flagNax = flagNax;
00161
00162 if(pSUBWIN_FEATURE(psubwin)->flagNax == TRUE){
00163 if(pSUBWIN_FEATURE(psubwin)->logflags[0] == 'n' && pSUBWIN_FEATURE(psubwin)->logflags[1] == 'n')
00164 {
00165 pSUBWIN_FEATURE(psubwin)->axes.auto_ticks[0] = FALSE;
00166 pSUBWIN_FEATURE(psubwin)->axes.auto_ticks[1] = FALSE;
00167
00168 CreatePrettyGradsFromNax(psubwin,aaint);
00169 }
00170 else{
00171 sciprint("Warning : Nax does not work with logarithmic scaling\n");}
00172 }
00173
00174 if(bounds_changed == TRUE || axes_properties_changed == TRUE)
00175 {
00176 sciDrawObj(sciGetCurrentFigure());
00177 }
00178
00179
00180 sciSetCurrentObj (ConstructFec
00181 ((sciPointObj *)
00182 sciGetCurrentSubWin(),
00183 x,y,triangles,func,*Nnode,*Ntr,zminmax,colminmax,colout, with_mesh));
00184
00185
00186 pptabofpointobj = sciGetCurrentObj();
00187 hdltab[cmpt]=sciGetHandle(pptabofpointobj);
00188 cmpt++;
00189 sciDrawObjIfRequired(sciGetCurrentObj ());
00190 DrawAxesIfRequired(sciGetCurrentObj ());
00192 if ((int)strlen(strflag) >=1 && strflag[0] == '1')
00193 {
00194 n1=1; styl[0]=1;styl[1]=0;
00195 sciSetCurrentObj (ConstructLegend
00196 (sciGetCurrentSubWin(),
00197 legend, strlen(legend), n1, styl, &pptabofpointobj));
00198
00199
00200
00201
00202
00203
00204
00205
00206
00207 sciDrawObjIfRequired(sciGetCurrentObj ());
00208 DrawAxesIfRequired(sciGetCurrentObj ());
00209 hdltab[cmpt]=sciGetHandle(sciGetCurrentObj ());
00210 cmpt++;
00211 }
00212 sciSetCurrentObj(ConstructCompound (hdltab, cmpt));
00215 return(0);
00216
00217 }
00218
00219 void newfec(integer *xm,integer *ym,double *triangles,double *func,integer *Nnode,
00220 integer *Ntr,double *zminmax,integer *colminmax, integer *colout, BOOL with_mesh)
00221 {
00222
00223
00224
00225
00226
00227
00228
00229 integer nz,i,j,k;
00230 integer verbose=0,whiteid,narg;
00231
00232 double *zlevel, dz, zmin, zmax, fxy[3], sx[3], sy[3];
00233 int *zone, *fill, kp, perm[3], zxy[3], color_min, color_max, col_under_min, col_upper_max;
00234 integer ii[3];
00235
00236
00237 integer WIRect[4];
00238 double Fxmin, Fxmax, Fymin, Fymax;
00239
00240 frame_clip_on();
00241
00242
00243
00244
00245
00246 if ( zminmax[0]==zminmax[1] )
00247 {
00248 zmin=(double) Mini(func,*Nnode); zmax=(double) Maxi(func,*Nnode);
00249 }
00250 else
00251 {
00252 zmin = Min( zminmax[0] , zminmax[1] ); zmax = Max( zminmax[0] , zminmax[1] );
00253 };
00254
00255
00256
00257
00258
00259
00260 C2F(dr)("xget","lastpattern",&verbose,&whiteid,&narg,
00261 PI0,PI0,PI0,PD0,PD0,PD0,PD0,0L,0L);
00262 nz=whiteid;
00263 if ( colminmax[0] == 0 && colminmax[1] == 0 )
00264 {
00265 color_min = 1;
00266 color_max = nz;
00267 }
00268 else if ( colminmax[0] < 1 || colminmax[1] > nz || colminmax[0] > colminmax[1] )
00269 {
00270 sciprint("\n\r fec : colminmax badly choosen ! ");
00271 return;
00272 }
00273 else
00274 {
00275 color_min = colminmax[0];
00276 color_max = colminmax[1];
00277 };
00278
00279
00280
00281
00282 if ( colout[0] < -1 || colout[0] > nz || colout[1] < -1 || colout[1] > nz )
00283 {
00284 sciprint("\n\r fec : colout badly choosen ! "); return;
00285 }
00286
00287 if ( colout[0] == -1 )
00288 col_under_min = color_min;
00289 else
00290 col_under_min = colout[0];
00291
00292 if ( colout[1] == -1 )
00293 col_upper_max = color_max;
00294 else
00295 col_upper_max = colout[1];
00296
00297
00298
00299
00300
00301
00302
00303
00304
00305
00306
00307
00308
00309
00310
00311
00312
00313
00314
00315 nz = color_max - color_min + 1;
00316 zone = MALLOC( *Nnode * sizeof(int) ) ;
00317 zlevel = MALLOC( (nz+1) * sizeof(double) ) ;
00318 fill = MALLOC( (nz+2) * sizeof(int) ) ;
00319 if ( (zone == NULL) || (zlevel == NULL) || (fill == NULL))
00320 {
00321 sciprint("fec: malloc No more Place\n");
00322 return;
00323 }
00324
00325
00326 fill[0] = -col_under_min;
00327 fill[1] = -color_min;
00328 for ( i = 2 ; i <= nz ; i++ ) fill[i] = fill[i-1] - 1;
00329 fill[nz+1] = -col_upper_max;
00330
00331
00332 dz = (zmax - zmin)/nz;
00333 for (i = 0 ; i < nz ; i++) zlevel[i] = zmin + i*dz;
00334 zlevel[nz] = zmax;
00335
00336
00337 for ( i = 0 ; i < (*Nnode) ; i++ )
00338 {
00339 if ( func[i] > zmax )
00340 zone[i] = nz+1;
00341 else if ( func[i] < zmin )
00342 zone[i] = 0;
00343 else
00344 zone[i] = (int) (floor( (func[i] - zmin)/dz ) + 1);
00345 };
00346
00347
00348
00349
00350
00351
00352 get_frame_in_pixel(WIRect);
00353 Fxmin = (double) WIRect[0]; Fymin = (double) WIRect[1];
00354 Fxmax = (double) WIRect[2]; Fymax = (double) WIRect[3];
00355
00356 for ( j = 0 ; j < *Ntr ; j++)
00357 {
00358 double xmin, xmax, ymin, ymax;
00359
00360 for ( k = 0 ; k < 3 ; k++ )
00361 {
00362 ii[k] = (integer) triangles[j+(*Ntr)*(k+1)] - 1;
00363 zxy[k] = zone[ii[k]];
00364 }
00365
00366
00367 PermutOfSort(zxy, perm);
00368
00369
00370
00371 for ( k = 0 ; k < 3 ; k++ )
00372 {
00373 kp = perm[k];
00374 sx[k] = xm[ii[kp]]; sy[k] = ym[ii[kp]];
00375 fxy[k] = func[ii[kp]]; zxy[k] = zone[ii[kp]];
00376 };
00377
00378
00379
00380 xmin = xmax = sx[0]; ymin = ymax = sy[0];
00381 if ( sx[1] < sx[2] )
00382 {
00383 xmin = Min(xmin,sx[1]); xmax = Max(xmax,sx[2]);
00384 }
00385 else
00386 {
00387 xmin = Min(xmin,sx[2]); xmax = Max(xmax,sx[1]);
00388 }
00389 if ( sy[1] < sy[2] )
00390 {
00391 ymin = Min(ymin,sy[1]); ymax = Max(ymax,sy[2]);
00392 }
00393 else
00394 {
00395 ymin = Min(ymin,sy[2]); ymax = Max(ymax,sy[1]);
00396 }
00397
00398 if ( xmax > Fxmin && ymax > Fymin && xmin < Fxmax && ymin < Fymax )
00399 {
00400
00401 PaintTriangle(sx, sy, fxy, zxy, zlevel, fill, with_mesh);
00402 }
00403 }
00404
00405 FREE( zone ) ;
00406 FREE( zlevel ) ;
00407 FREE( fill ) ;
00408
00409
00410 frame_clip_off();
00411 }
00412
00413
00414
00415
00416
00417
00418 static void PermutOfSort (int *tab, int *perm)
00419 {
00420
00421
00422
00423 perm[0]=0; perm[1] = 1; perm[2] = 2;
00424 if ( tab[1] < tab[0] )
00425 {
00426 perm[1]=0 ; perm[0] = 1;
00427 };
00428 if ( tab[2] < tab[perm[1]] )
00429 {
00430 if ( tab[2] < tab[perm[0]] )
00431 {
00432 perm[2] = perm[1]; perm[1] = perm[0]; perm[0] = 2;
00433 }
00434 else
00435 {
00436 perm[2] = perm[1] ; perm[1] = 2;
00437 };
00438 };
00439 }
00440
00441 static void PaintTriangle (double *sx, double *sy, double *fxy, int *zxy,
00442 double *zlevel, int *fill, BOOL with_mesh)
00443 {
00444
00445
00446
00447
00448
00449
00450
00451
00452
00453
00454
00455
00456
00457
00458
00459
00460 int nb0, edge, izone, color;
00461 integer ncont,nr, zero=0, resx[5],resy[5];
00462 integer xEdge2, yEdge2, xEdge, yEdge;
00463
00464 if ( zxy[0] == zxy[2] )
00465 {
00466 resx[0]=inint(sx[0]); resx[1]=inint(sx[1]); resx[2]=inint(sx[2]);
00467 resy[0]=inint(sy[0]); resy[1]=inint(sy[1]); resy[2]=inint(sy[2]);
00468 color = fill[zxy[0]]; nr = 3;
00469 if ( color != 0 )
00470 {
00471 C2F(dr)("xliness","str",resx,resy,&color,(ncont=1,&ncont),&nr,
00472 PI0,PD0,PD0,PD0,PD0,0L,0L);
00473 }
00474 if ( with_mesh )
00475 {
00476 C2F(dr)("xliness","str",resx,resy,&zero,(ncont=1,&ncont),&nr,
00477 PI0,PD0,PD0,PD0,PD0,0L,0L);
00478 }
00479 return;
00480 }
00481
00482
00483
00484
00485
00486
00487
00488
00489
00490
00491
00492
00493
00494
00495
00496
00497
00498
00499 nb0 = zxy[1]-zxy[0];
00500
00501
00502
00503
00504
00505 resx[0]=inint(sx[0]); resy[0]=inint(sy[0]); nr = 1; edge = 0;
00506 if ( nb0 == 0 )
00507 {
00508 resx[1] = inint(sx[1]);
00509 resy[1] = inint(sy[1]);
00510 nr++;
00511 edge = 1;
00512 }
00513 else
00514 {
00515 nb0--;
00516 }
00517
00518 FindIntersection(sx, sy, fxy, zlevel[zxy[0]], edge, edge+1, &xEdge, &yEdge);
00519 resx[nr] = xEdge;
00520 resy[nr] = yEdge;
00521 nr++;
00522
00523 FindIntersection(sx, sy, fxy, zlevel[zxy[0]], 0, 2, &xEdge2, &yEdge2);
00524 resx[nr] = xEdge2;
00525 resy[nr] = yEdge2;
00526 nr++;
00527 color = fill[zxy[0]];
00528 if ( color != 0 )
00529 {
00530 C2F(dr)("xliness","str",resx,resy,&color,(ncont=1,&ncont),&nr,
00531 PI0,PD0,PD0,PD0,PD0,0L,0L);
00532 }
00533
00534
00535
00536
00537
00538 for ( izone = zxy[0]+1 ; izone < zxy[2] ; izone++ )
00539 {
00540 resx[0] = xEdge2;
00541 resy[0] = yEdge2;
00542 resx[1] = xEdge ;
00543 resy[1] = yEdge ;
00544 nr = 2 ;
00545 if ( edge == 0 )
00546 {
00547 if (nb0 == 0 )
00548 {
00549 resx[2] = inint(sx[1]);
00550 resy[2] = inint(sy[1]);
00551 nr++;
00552 edge = 1;
00553 }
00554 else
00555 {
00556 nb0--;
00557 }
00558 }
00559
00560 FindIntersection(sx, sy, fxy, zlevel[izone], edge, edge+1, &xEdge, &yEdge);
00561 resx[nr]=xEdge; resy[nr]=yEdge; nr++;
00562
00563 FindIntersection(sx, sy, fxy, zlevel[izone], 0, 2, &xEdge2, &yEdge2);
00564 resx[nr]=xEdge2; resy[nr]=yEdge2; nr++;
00565 color = fill[izone];
00566 if ( color != 0 )
00567 {
00568 C2F(dr)("xliness","str",resx,resy,&color,(ncont=1,&ncont),&nr,
00569 PI0,PD0,PD0,PD0,PD0,0L,0L);
00570 }
00571 }
00572
00573
00574
00575
00576 resx[0] = xEdge2;
00577 resy[0] = yEdge2;
00578 resx[1] = xEdge;
00579 resy[1] = yEdge;
00580 nr = 2;
00581 if ( edge == 0 )
00582 {
00583 resx[2]=inint(sx[1]);
00584 resy[2]=inint(sy[1]);
00585 nr++;
00586 } ;
00587
00588 resx[nr] = inint(sx[2]);
00589 resy[nr] = inint(sy[2]);
00590 nr++;
00591 color = fill[zxy[2]];
00592 if ( color != 0 )
00593 {
00594 C2F(dr)("xliness","str",resx,resy,&color,(ncont=1,&ncont),&nr,
00595 PI0,PD0,PD0,PD0,PD0,0L,0L);
00596 }
00597
00598 if ( with_mesh )
00599 {
00600 resx[0]=inint(sx[0]); resx[1]=inint(sx[1]); resx[2]=inint(sx[2]);
00601 resy[0]=inint(sy[0]); resy[1]=inint(sy[1]); resy[2]=inint(sy[2]);
00602 nr = 3;
00603 C2F(dr)("xliness","str",resx,resy,&zero,(ncont=1,&ncont),&nr,
00604 PI0,PD0,PD0,PD0,PD0,0L,0L);
00605 }
00606 }
00607
00608 static void FindIntersection(double *sx, double *sy, double *fxy, double z,
00609 int inda, int indb, integer *xint, integer *yint)
00610 {
00611 double alpha;
00612 alpha = (z - fxy[inda])/(fxy[indb] - fxy[inda]);
00613 *xint = inint((1 - alpha)*sx[inda] + alpha*sx[indb]);
00614 *yint = inint((1 - alpha)*sy[inda] + alpha*sy[indb]);
00615 }
00616
00617
00618
00619
00620
00621
00622
00623
00624
00625