1 #include "coxplot.h"
2 #include <math.h>
3
4 /*****************************************************************************
5 This software is copyrighted and owned by the Medical College of Wisconsin.
6 See the file README.Copyright for details.
7 ******************************************************************************/
8
9 /*------------------------------------------------------------------------*/
10
11 #ifndef WAY_BIG
12 # define WAY_BIG 1.e+10
13 #endif
14
15 static float p10( float x ) ; /* prototype */
16
17 #undef NCLR_MAX
18 #define NCLR_MAX 99
19 static float ccc[NCLR_MAX][3] = {
20 { 0.0 , 0.0 , 0.0 } ,
21 { 0.9 , 0.0 , 0.0 } ,
22 { 0.0 , 0.7 , 0.0 } ,
23 { 0.0 , 0.0 , 0.9 } ,
24 { 0.8 , 0.0 , 0.9 } ,
25 { 0.7 , 0.6 , 0.0 } ,
26 { 0.0 , 0.7 , 0.7 }
27 } ;
28
29 static int use_ddd = 0 ;
30 static int ddd[NCLR_MAX] = { 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
31 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
32 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
33 1,1,1,1,1,1,1,1,1 } ;
34
35 static int NCLR = 7 ;
36 static int dont_init_colors=0 ;
37
38 static int ilab[4] = { 0,2,3,1 } ; /* whether to plot labels on axes */
39
40 #define STGOOD(s) ( (s) != NULL && (s)[0] != '\0' )
41
42 #define SY 0.07
43
44 static float THIK = 0.004f ; /* 27 Mar 2004: changed from a #define */
45 static float thik = 0.002f ; /* 02 Apr 2012: for labels */
46
47 static float aspect = 1.3f ; /* 03 May 2018 */
48 static int do_perim = 1 ;
49 static int do_naked = 0 ;
50
51 #define ASX(xv) ((xv)*aspect/1.3f)
52
plot_ts_set_aspect(float asp)53 void plot_ts_set_aspect( float asp ){ aspect = asp ; }
plot_ts_do_perim(int dp)54 void plot_ts_do_perim ( int dp ){ do_perim = dp ; }
55
plot_ts_do_naked(int nn)56 void plot_ts_do_naked ( int nn ){
57 do_naked = nn ;
58 if( do_naked ) do_perim = 0 ;
59 }
60
61 /*----------------------------------------------------------------------*/
62 static float tsbox = 0.0f ; /* 23 May 2011 */
63 static float dboxs = 0.006f ;
64 static float noline = 0 ;
65 static int dohist = 0 ; /* 10 Jul 2014 */
66
plot_ts_dobox(float a)67 void plot_ts_dobox( float a ){ tsbox = a ; }
plot_ts_noline(int a)68 void plot_ts_noline( int a ){ noline = a ; }
plot_ts_dohist(int a)69 void plot_ts_dohist( int a ){ dohist = a ; }
70
plot_one_diamond(float xx,float yy)71 static void plot_one_diamond( float xx , float yy )
72 {
73 float dbbbb = (tsbox > 0.0f) ? tsbox : dboxs ;
74 float x , y ;
75 plotpak_zzphys( xx , yy , &x , &y ) ;
76 plotpak_phline( x+dbbbb , y , x , y+dbbbb ) ;
77 plotpak_phline( x , y+dbbbb , x-dbbbb , y ) ;
78 plotpak_phline( x-dbbbb , y , x , y-dbbbb ) ;
79 plotpak_phline( x , y-dbbbb , x+dbbbb , y ) ;
80 }
81
plot_one_hexagon(float xx,float yy)82 static void plot_one_hexagon( float xx , float yy )
83 {
84 float dbbbb = (tsbox > 0.0f) ? tsbox : dboxs ;
85 float x , y , da=0.5f*dbbbb , db=0.866f*dbbbb ;
86 plotpak_zzphys( xx , yy , &x , &y ) ;
87 plotpak_phline( x , y+dbbbb , x-db , y+dbbbb-da ) ;
88 plotpak_phline( x-db , y+dbbbb-da , x-db , y-dbbbb+da ) ;
89 plotpak_phline( x-db , y-dbbbb+da , x , y-dbbbb ) ;
90 plotpak_phline( x , y-dbbbb , x+db , y-dbbbb+da ) ;
91 plotpak_phline( x+db , y-dbbbb+da , x+db , y+dbbbb-da ) ;
92 plotpak_phline( x+db , y+dbbbb-da , x , y+dbbbb ) ;
93 }
94
plot_one_square(float xx,float yy)95 static void plot_one_square( float xx , float yy )
96 {
97 float dbbbb = (tsbox > 0.0f) ? tsbox : dboxs ;
98 float x , y ;
99 plotpak_zzphys( xx , yy , &x , &y ) ;
100 plotpak_phline( x-dbbbb , y-dbbbb , x+dbbbb , y-dbbbb ) ;
101 plotpak_phline( x+dbbbb , y-dbbbb , x+dbbbb , y+dbbbb ) ;
102 plotpak_phline( x+dbbbb , y+dbbbb , x-dbbbb , y+dbbbb ) ;
103 plotpak_phline( x-dbbbb , y+dbbbb , x-dbbbb , y-dbbbb ) ;
104 }
105
plot_one_utriang(float xx,float yy)106 static void plot_one_utriang( float xx , float yy )
107 {
108 float dbbbb = (tsbox > 0.0f) ? tsbox : dboxs ;
109 float x , y , da=0.5f*dbbbb , db=0.866f*dbbbb ;
110 plotpak_zzphys( xx , yy , &x , &y ) ;
111 plotpak_phline( x , y+dbbbb , x-db , y-da ) ;
112 plotpak_phline( x-db , y-da , x+db , y-da ) ;
113 plotpak_phline( x+db , y-da , x , y+dbbbb ) ;
114 }
115
plot_one_dtriang(float xx,float yy)116 static void plot_one_dtriang( float xx , float yy )
117 {
118 float dbbbb = (tsbox > 0.0f) ? tsbox : dboxs ;
119 float x , y , da=0.5f*dbbbb , db=0.866f*dbbbb ;
120 plotpak_zzphys( xx , yy , &x , &y ) ;
121 plotpak_phline( x , y-dbbbb , x-db , y+da ) ;
122 plotpak_phline( x-db , y+da , x+db , y+da ) ;
123 plotpak_phline( x+db , y+da , x , y-dbbbb ) ;
124 }
125
126 #undef CIRCNUM
127 #define CIRCNUM 16
128 static float circc[CIRCNUM+1] , circs[CIRCNUM+1] ;
129
circ_setup(void)130 static void circ_setup(void)
131 {
132 static int circdone=0 ; int ii ;
133 if( circdone ) return ;
134 for( ii=0 ; ii < CIRCNUM+1 ; ii++ ){
135 circc[ii] = cosf(2.0f*3.141592f*ii/(float)CIRCNUM) ;
136 circs[ii] = sinf(2.0f*3.141592f*ii/(float)CIRCNUM) ;
137 }
138 circdone = 1 ;
139 }
140
plot_one_circle(float xx,float yy)141 static void plot_one_circle( float xx , float yy )
142 {
143 float dbbbb = (tsbox > 0.0f) ? tsbox : dboxs ;
144 float x , y ; int ii ;
145 circ_setup() ;
146 plotpak_zzphys( xx , yy , &x , &y ) ;
147 for( ii=0 ; ii < CIRCNUM ; ii++ )
148 plotpak_phline( x+dbbbb*circc[ii], y+dbbbb*circs[ii], x+dbbbb*circc[ii+1], y+dbbbb*circs[ii+1] ) ;
149 }
150
plot_one_stellar(float xx,float yy)151 static void plot_one_stellar( float xx , float yy )
152 {
153 float dbbbb = (tsbox > 0.0f) ? tsbox : dboxs ;
154 float x , y , dt=0.5f*dbbbb ; int ii ;
155 circ_setup() ;
156 plotpak_zzphys( xx , yy , &x , &y ) ;
157 for( ii=0 ; ii < CIRCNUM ; ii+=2 ){
158 plotpak_phline( x+dbbbb*circc[ii], y+dbbbb*circs[ii], x+dt*circc[ii+1], y+dt*circs[ii+1] ) ;
159 plotpak_phline( x+dt*circc[ii+1], y+dt*circs[ii+1], x+dbbbb*circc[ii+2], y+dbbbb*circs[ii+2] ) ;
160 }
161 }
162
plot_onebox(float xx,float yy,int kk)163 static void plot_onebox( float xx , float yy , int kk )
164 {
165 switch( kk%7 ){ /* choose box shape depending on which curve is being plotted */
166 default:
167 case 0: plot_one_diamond(xx,yy) ; break ;
168 case 1: plot_one_circle (xx,yy) ; break ;
169 case 2: plot_one_utriang(xx,yy) ; break ;
170 case 3: plot_one_stellar(xx,yy) ; break ;
171 case 4: plot_one_square (xx,yy) ; break ;
172 case 5: plot_one_dtriang(xx,yy) ; break ;
173 case 6: plot_one_hexagon(xx,yy) ; break ;
174 }
175 }
176 /*---------------------------------------------------------------------------*/
177
ts_gcd(int m,int n)178 static int ts_gcd( int m , int n ) /* Euclid's Greatest Common Denominator */
179 {
180 while( m > 0 ){
181 if( n > m ){ int t=m; m=n; n=t; } /* swap */
182 m -= n ;
183 }
184 return n ;
185 }
186
187 /*---------------------------------------------------------------------------*/
188
ts_find_relprime(int n)189 static int ts_find_relprime( int n ) /* find number relatively prime to n */
190 {
191 int dj , n5=n/5 ;
192 if( n5 < 2 ) return 1 ;
193 for( dj=n5 ; ts_gcd(n,dj) > 1 ; dj++ ) ; /*nada*/
194 return dj ;
195 }
196
197 /*----------------------------------------------------------------------*/
198 static int xpush=1 , ypush=1 ;
199
plot_ts_xypush(int a,int b)200 void plot_ts_xypush( int a , int b ){ xpush=a; ypush=b; } /* 12 Mar 2003 */
201
202 static float xxbot,xxtop , yybot,yytop ;
203 static int nnaxx=-1,mmaxx=-1 , nnayy=-1,mmayy=-1 ;
204
plot_ts_xfix(int nax,int max,float xb,float xt)205 void plot_ts_xfix( int nax, int max, float xb, float xt ) /* 22 Jul 2003 */
206 {
207 nnaxx = nax ; mmaxx = max ; xxbot = xb ; xxtop = xt ;
208 }
209
plot_ts_yfix(int nay,int may,float yb,float yt)210 void plot_ts_yfix( int nay, int may, float yb, float yt )
211 {
212 nnayy = nay ; mmayy = may ; yybot = yb ; yytop = yt ;
213 }
214
215 /*----------------------------------------------------------------------*/
216 /* Check to define colors for plotting from environment variables.
217 ------------------------------------------------------------------------*/
218
init_colors(void)219 static void init_colors(void)
220 {
221 static int first=1 ;
222 char ename[32] , *eee ;
223 float rf,gf,bf ;
224 int ii ;
225
226 if( dont_init_colors ){ first=1 ; return; }
227 if( !first ) return ;
228 first = 0 ;
229
230 /* init ii to 0 (was 1) to match README.environment: 19 May 2004 [rickr] */
231
232 for( ii=0 ; ii < NCLR_MAX ; ii++ ){
233 sprintf(ename,"AFNI_1DPLOT_COLOR_%02d",ii+1) ;
234 eee = getenv(ename) ;
235 if( eee == NULL && ii < 9 ){ /** 21 Apr 2005: check alternatives **/
236 sprintf(ename,"AFNI_1DPLOT_COLOR_%1d",ii+1) ; eee = getenv(ename) ;
237 }
238 if( eee == NULL && ii <= 9 ){
239 sprintf(ename,"AFNI_1DPLOT_COLOR_O%1d",ii+1) ; eee = getenv(ename) ;
240 }
241 if( eee != NULL && *eee != '\0' ){
242 rf=gf=bf = -1.0 ;
243 (void)sscanf( eee , "rgbi:%f/%f/%f" , &rf,&gf,&bf ) ;
244 if( rf >= 0.0 && rf <= 1.0 &&
245 gf >= 0.0 && gf <= 1.0 &&
246 bf >= 0.0 && bf <= 1.0 ){
247
248 ccc[ii][0] = rf ; ccc[ii][1] = gf ; ccc[ii][2] = bf ;
249 NCLR = ii+1 ;
250 } else if( strcasecmp(eee,"green") == 0 ){
251 ccc[ii][0] = 0.0f; ccc[ii][1] = 0.8f; ccc[ii][2] = 0.0f; NCLR = ii+1;
252 } else if( strcasecmp(eee,"red") == 0 ){
253 ccc[ii][0] = 0.8f; ccc[ii][1] = 0.0f; ccc[ii][2] = 0.0f; NCLR = ii+1;
254 } else if( strcasecmp(eee,"blue") == 0 ){
255 ccc[ii][0] = 0.0f; ccc[ii][1] = 0.0f; ccc[ii][2] = 0.8f; NCLR = ii+1;
256 } else if( strcasecmp(eee,"black") == 0 ){
257 ccc[ii][0] = 0.0f; ccc[ii][1] = 0.0f; ccc[ii][2] = 0.0f; NCLR = ii+1;
258 } else if( strcasecmp(eee,"purple") == 0 || strcasecmp(eee,"violet") == 0 ){
259 ccc[ii][0] = 0.8f; ccc[ii][1] = 0.0f; ccc[ii][2] = 0.8f; NCLR = ii+1;
260 } else if( strcasecmp(eee,"gold") == 0 || strcasecmp(eee,"yellow") == 0 ){
261 ccc[ii][0] = 0.8f; ccc[ii][1] = 0.6f; ccc[ii][2] = 0.0f; NCLR = ii+1;
262 } else if( strcasecmp(eee,"pink") == 0 ){
263 ccc[ii][0] = 0.9f; ccc[ii][1] = 0.3f; ccc[ii][2] = 0.5f; NCLR = ii+1;
264 } else if( strcasecmp(eee,"cyan") == 0 ){
265 ccc[ii][0] = 0.0f; ccc[ii][1] = 0.7f; ccc[ii][2] = 0.7f; NCLR = ii+1;
266 } else if( *eee == '#' && *(eee+1) != '\0' ){
267 int le=strlen(eee+1) , val , bas , rr,gg,bb ;
268 val = (int)strtol( eee+1 , NULL , 16 ) ;
269 bas = (le <= 3) ? 16 : 256 ;
270 bb = val % bas ; val = val / bas ; bf = bb / ((float)bas) ;
271 gg = val % bas ; val = val / bas ; gf = gg / ((float)bas) ;
272 rr = val % bas ; rf = rr / ((float)bas) ;
273 ccc[ii][0] = rf ; ccc[ii][1] = gf ; ccc[ii][2] = bf ; NCLR = ii+1 ;
274 } else {
275 int jj = find_color_name(eee,&rf,&gf,&bf) ;
276 if( jj >= 0 ){
277 ccc[ii][0] = rf ; ccc[ii][1] = gf ; ccc[ii][2] = bf ; NCLR = ii+1 ;
278 } else {
279 fprintf(stderr, "** ERROR: %s = %s is not a recognizable color\n", ename,eee ) ;
280 fprintf(stderr, " Recognizable color names include\n"
281 " green red blue black purple gold pink cyan OR #xxxxxx\n"
282 " where 'xxxxxx' is 6 hex digits for RGB.\n" ) ;
283 }
284 }
285 }
286 }
287
288 eee = getenv("AFNI_1DPLOT_THIK") ; /* 27 Mar 2004 */
289 if( eee == NULL ) eee = getenv("AFNI_1DPLOT_THICK") ; /* 15 Apr 2009 */
290 if( eee != NULL ){
291 rf = (float)strtod(eee,NULL) ; plot_ts_setTHIK(rf) ;
292 }
293 }
294
295 /*-----------------------------------------------------------------------*/
296 /* 23 Nov 2007: set colors explicitly */
297
plot_ts_setcolors(int ncol,float * rrr,float * ggg,float * bbb)298 void plot_ts_setcolors( int ncol , float *rrr , float *ggg , float *bbb )
299 {
300 int ii ;
301
302 if( ncol <= 0 || rrr==NULL || ggg==NULL || bbb==NULL ){
303 NCLR = 4 ; dont_init_colors=0 ;
304 ccc[0][0] = 0.0 ; ccc[0][1] = 0.0 ; ccc[0][2] = 0.0 ;
305 ccc[1][0] = 0.9 ; ccc[1][1] = 0.0 ; ccc[1][2] = 0.0 ;
306 ccc[2][0] = 0.0 ; ccc[2][1] = 0.7 ; ccc[2][2] = 0.0 ;
307 ccc[3][0] = 0.0 ; ccc[3][1] = 0.0 ; ccc[3][2] = 0.9 ;
308 } else {
309 if( ncol > NCLR_MAX ) ncol = NCLR_MAX ;
310 dont_init_colors = 1 ;
311 for( ii=0 ; ii < ncol ; ii++ ){
312 ccc[ii][0] = rrr[ii] ; ccc[ii][1] = ggg[ii] ; ccc[ii][2] = bbb[ii] ;
313 }
314 if( ncol > NCLR ) NCLR = ncol ;
315 }
316 return ;
317 }
318
319 /*-----------------------------------------------------------------------*/
320
plot_ts_setdash(int ndash,int * code)321 void plot_ts_setdash( int ndash , int *code )
322 {
323 int ii ;
324 if( ndash <= 0 || code == NULL ){ use_ddd = 0 ; return ; }
325 if( ndash > NCLR_MAX ) ndash = NCLR_MAX ;
326 for( ii=0 ; ii < ndash ; ii++ ) ddd[ii] = code[ii] ;
327 use_ddd = 1 ;
328 return ;
329 }
330
331 /*-----------------------------------------------------------------------*/
332
plot_ts_setTHIK(float thk)333 void plot_ts_setTHIK( float thk ) /* for lines */
334 {
335 if( thk < 0.001f ) THIK = 0.001f ;
336 else if( thk > 0.020f ) THIK = 0.020f ;
337 else THIK = thk ;
338 }
339
plot_ts_setthik(float thk)340 void plot_ts_setthik( float thk ) /* for labels */
341 {
342 if( thk < 0.000f ) thik = 0.000f ;
343 else if( thk > 0.005f ) thik = 0.005f ;
344 else thik = thk ;
345 }
346
347 /*-----------------------------------------------------------------------*/
348
349 static int thik_n1 = -666 , thik_n2 = -999 ;
350 static float thik_12 = 0.002f ;
351
plot_ts_setthik_12(int n1,int n2,float thk)352 void plot_ts_setthik_12( int n1, int n2, float thk )
353 {
354 if( n1 < 0 || n2 < n1 ){
355 thik_n1 = -666 ; thik_n2 = -999 ;
356 } else {
357 thik_n1 = n1 ; thik_n2 = n2 ;
358 if( thk < 0.000f ) thik_12 = 0.000f ;
359 else if( thk > 0.005f ) thik_12 = 0.005f ;
360 else thik_12 = thk ;
361 }
362 }
363
364 /*-----------------------------------------------------------------------*/
365
366 #undef VBOX
367 #define VBOX 1
368
369 #undef RBOX
370 #define RBOX 2 /* 29 Jan 2017 */
371
372 #undef TLIN
373 #define TLIN 3 /* 19 Sep 2017 */
374
375 typedef struct {
376 int code ;
377 int ygr ;
378 float x1 , x2 ;
379 float rr , gg , bb ;
380 float rb_y1 , rb_y2 , rb_y3 , /* RBOX stuff [29 Jan 2017] */
381 rb_rr,rb_gg,rb_bb ;
382 int dcode ; /* for TLIN: dashcode */
383 } TS_vbox ;
384
385 static int nvbox = 0 ;
386 static TS_vbox *vbox = NULL ;
387
plot_ts_add_vbox(int ygr,float x1,float x2,float rr,float gg,float bb)388 void plot_ts_add_vbox( int ygr , float x1 , float x2 ,
389 float rr , float gg , float bb )
390 {
391 vbox = (TS_vbox *)realloc( (void *)vbox , sizeof(TS_vbox)*(nvbox+1) ) ;
392 vbox[nvbox].code = VBOX ;
393 vbox[nvbox].ygr = ygr ;
394 vbox[nvbox].x1 = x1 ;
395 vbox[nvbox].x2 = x2 ;
396 vbox[nvbox].rr = rr ;
397 vbox[nvbox].gg = gg ;
398 vbox[nvbox].bb = bb ;
399 nvbox++ ;
400 }
401
plot_ts_add_rbox(int ygr,float x1,float y1,float x2,float y2,float y3,float rr,float gg,float bb,float r2,float g2,float b2)402 void plot_ts_add_rbox( int ygr ,
403 float x1,float y1 , float x2,float y2,float y3 ,
404 float rr,float gg,float bb,
405 float r2,float g2,float b2 ) /* 29 Jan 2017 */
406 {
407 vbox = (TS_vbox *)realloc( (void *)vbox , sizeof(TS_vbox)*(nvbox+1) ) ;
408 vbox[nvbox].code = RBOX ;
409 vbox[nvbox].ygr = ygr ;
410 vbox[nvbox].x1 = x1 ;
411 vbox[nvbox].x2 = x2 ;
412 vbox[nvbox].rr = rr ;
413 vbox[nvbox].gg = gg ;
414 vbox[nvbox].bb = bb ;
415
416 vbox[nvbox].rb_y1 = y1 ; /* spec for rectangle (RBOX) */
417 vbox[nvbox].rb_y2 = y2 ; /* with filled color (above) */
418 vbox[nvbox].rb_y3 = y3 ; /* with filled color (above) */
419 vbox[nvbox].rb_rr = r2 ; /* and outline around it (color here) */
420 vbox[nvbox].rb_gg = g2 ;
421 vbox[nvbox].rb_bb = b2 ;
422 nvbox++ ;
423 }
424
plot_ts_add_tlin(int ygr,float x1,float y1,float x2,float y2,float rr,float gg,float bb,int dcode)425 void plot_ts_add_tlin( int ygr ,
426 float x1,float y1 , float x2,float y2 ,
427 float rr,float gg,float bb,int dcode ) /* 19 Sep 2017 */
428 {
429 vbox = (TS_vbox *)realloc( (void *)vbox , sizeof(TS_vbox)*(nvbox+1) ) ;
430 vbox[nvbox].code = TLIN ;
431 vbox[nvbox].ygr = ygr ;
432 vbox[nvbox].x1 = x1 ;
433 vbox[nvbox].x2 = x2 ;
434 vbox[nvbox].rr = rr ;
435 vbox[nvbox].gg = gg ;
436 vbox[nvbox].bb = bb ;
437
438 vbox[nvbox].rb_y1 = y1 ; /* spec for line (TLIN) */
439 vbox[nvbox].rb_y2 = y2 ; /* with filled color (above) */
440 vbox[nvbox].dcode = dcode ; /* dash code */
441 nvbox++ ;
442 }
443
plot_ts_clear_vbox(void)444 void plot_ts_clear_vbox(void)
445 {
446 if( vbox != NULL ) free(vbox) ;
447 vbox = NULL ; nvbox = 0 ; return ;
448 }
449
450 /*-----------------------------------------------------------------------*/
451
452 static int nsepx = 0 ;
453 static int *lsepx = NULL ;
454 static float **sepx = NULL ;
455
456 static float sepx_bot=-1.0f , sepx_top=1.0f ;
457
plot_ts_fetch_sepx(int * ns,int ** ls,float *** sx)458 void plot_ts_fetch_sepx( int *ns , int **ls , float ***sx )
459 {
460 if( ns != NULL ) *ns = nsepx ;
461 if( ls != NULL ) *ls = lsepx ;
462 if( sx != NULL ) *sx = sepx ;
463 }
464
plot_ts_clear_sepx(void)465 void plot_ts_clear_sepx(void)
466 {
467 if( lsepx != NULL ) free(lsepx) ;
468 if( nsepx > 0 && sepx != NULL ){
469 int kk ;
470 for( kk=0 ; kk < nsepx ; kk++ ) free(sepx[kk]) ;
471 free(sepx) ;
472 }
473 nsepx = 0 ; sepx = NULL ; lsepx = NULL ; return ;
474 }
475
plot_ts_add_sepx(int lx,float * x)476 void plot_ts_add_sepx( int lx , float *x )
477 {
478 int kk ;
479
480 if( lx < 2 || x == NULL ) return ;
481 lsepx = (int * )realloc( lsepx , sizeof(int) *(nsepx+1) ) ;
482 sepx = (float **)realloc( sepx , sizeof(float *)*(nsepx+1) ) ;
483 sepx[nsepx] = (float *)malloc( sizeof(float)*lx ) ;
484 lsepx[nsepx] = lx ;
485 for( kk=0 ; kk < lx ; kk++ ) sepx[nsepx][kk] = x[kk] ;
486 nsepx++ ; return ;
487 }
488
plot_ts_sepx_getstats(void)489 static void plot_ts_sepx_getstats(void)
490 {
491 int ss , ii ; float bb , tt ;
492
493 if( nsepx <= 0 || lsepx == NULL || sepx == NULL ) return ;
494
495 bb = tt = sepx[0][0] ;
496 for( ss=0 ; ss < nsepx ; ss++ ){
497 for( ii=0 ; ii < lsepx[ss] ; ii++ ){
498 if( sepx[ss][ii] < bb ) bb = sepx[ss][ii] ;
499 if( sepx[ss][ii] > tt ) tt = sepx[ss][ii] ;
500 }
501 }
502 if( bb < tt ){
503 sepx_bot = bb ; sepx_top = tt ;
504 } else {
505 sepx_bot = bb-1.0f ; sepx_top = bb+1.0f ;
506 }
507 }
508
509 /*-----------------------------------------------------------------------
510 Plot some timeseries data into an in-memory plot structure, which
511 must be displayed later in some fashion.
512 If array x[] is NULL, then routine will make an x-axis up.
513
514 ymask details what to do with y graphs:
515 ymask & TSP_SEPARATE_YBOX => individual boxes for each y[i][]
516 ymask & TSP_SEPARATE_YSCALE => and individual scales
517
518 27 Jan 1999: all routines are modified to leave the plotpak_set()
519 transform for the data at box #0 as the last setting
520
521 21 Oct 2013: if global variable nsepx > 0, then the x[] axis is ignored
522 -------------------------------------------------------------------------*/
523
plot_ts_mem(int nx,float * x,int ny,int ymask,float ** y,char * lab_xxx,char * lab_yyy,char * lab_top,char ** nam_yyy)524 MEM_plotdata * plot_ts_mem( int nx , float *x , int ny , int ymask , float **y ,
525 char *lab_xxx , char *lab_yyy , char *lab_top ,
526 char **nam_yyy )
527 {
528 int ii , jj , np , nnax,nnay , mmax,mmay ;
529 float *xx=NULL , *yy=NULL ;
530 float xbot,xtop , ybot,ytop , pbot,ptop , xobot,xotop,yobot,yotop ;
531 float xabot,xatop ; int xflip=0 ;
532 char str[32] ;
533 int yall , ysep , ixtop ;
534 float *ylo , *yhi , yll,yhh ;
535 MEM_plotdata *mp ;
536 float xb1,xb2,yb1,yb2,yb3 ; int iv ;
537 float thth ;
538 int dashno=1 ;
539
540 /*-- sanity check --*/
541
542 if( nx <= 1 || ny == 0 || y == NULL ) return NULL ;
543
544 init_colors() ;
545
546 if( do_naked ){ /* 03 May 2018 */
547 lab_xxx = lab_yyy = NULL ; nam_yyy = NULL ;
548 }
549 if( do_naked > 1 ){
550 lab_top = NULL ;
551 }
552
553 /*-- make up an x-axis if none given --*/
554
555 if( nsepx > 0 ){
556 plot_ts_sepx_getstats() ;
557 xbot = sepx_bot ;
558 xtop = sepx_top ;
559 } else if( x == NULL ){
560 xx = (float *) malloc( sizeof(float) * nx ) ;
561 for( ii=0 ; ii < nx ; ii++ ) xx[ii] = ii ;
562 xbot = 0 ; xtop = nx-1 ;
563 } else {
564 xx = x ;
565 xbot = WAY_BIG ; xtop = -WAY_BIG ;
566 for( ii=0 ; ii < nx ; ii++ ){
567 if( xx[ii] < xbot && fabsf(xx[ii]) < WAY_BIG ) xbot = xx[ii] ;
568 if( xx[ii] > xtop && fabsf(xx[ii]) < WAY_BIG ) xtop = xx[ii] ;
569 }
570 if( xbot >= xtop ) return NULL ;
571 }
572
573 /*-- push range of x outwards --*/
574
575 pbot = p10(xbot) ; ptop = p10(xtop) ; if( ptop < pbot ) ptop = pbot ;
576 if( nnaxx >= 0 ){
577 nnax = nnaxx ;
578 mmax = mmaxx ;
579 xabot = xxbot ;
580 xatop = xxtop ;
581 xbot = MIN(xabot,xatop) ;
582 xtop = MAX(xabot,xatop) ;
583 } else if( ptop != 0.0f && xpush > 0 ){
584 np = (xtop-xbot) / ptop ;
585 switch( np ){
586 case 1: ptop *= 0.1f ; break ;
587 case 2: ptop *= 0.2f ; break ;
588 case 3: ptop *= 0.25f ; break ;
589 case 4:
590 case 5: ptop *= 0.5f ; break ;
591 }
592 xbot = floor( xbot/ptop ) * ptop ; xabot = xbot ;
593 xtop = ceil( xtop/ptop ) * ptop ; xatop = xtop ;
594 nnax = floor( (xtop-xbot) / ptop + 0.5f ) ;
595 mmax = (nnax < 3) ? 10
596 : (nnax < 6) ? 5 : 2 ;
597 } else {
598 nnax = 1 ; mmax = 10 ;
599 ii = (int)rint(xtop-xbot) ;
600 if( fabs(xtop-xbot-ii) < 0.01 && ii <= 200 ) mmax = ii ;
601 xabot = xbot ; xatop = xtop ;
602 }
603 xflip = (xabot > xatop) ;
604
605 /*-- find range of y --*/
606
607 yall = (ny == 1) || ((ymask & TSP_SEPARATE_YBOX) == 0) ;
608 ysep = (ymask & TSP_SEPARATE_YSCALE) != 0 ;
609 /* Nov 1998: find range of */
610 ylo = (float *) malloc(sizeof(float)*ny) ; /* each array separately. */
611 yhi = (float *) malloc(sizeof(float)*ny) ;
612
613 ybot = WAY_BIG ; ytop = -WAY_BIG ;
614 for( jj=0 ; jj < ny ; jj++ ){
615 yy = y[jj] ; yll = WAY_BIG ; yhh = -WAY_BIG ;
616 for( ii=0 ; ii < nx ; ii++ ){
617 if( yy[ii] < yll && fabsf(yy[ii]) < WAY_BIG ) yll = yy[ii] ;
618 if( yy[ii] > yhh && fabsf(yy[ii]) < WAY_BIG ) yhh = yy[ii] ;
619 }
620 ylo[jj] = yll ; yhi[jj] = yhh ;
621 if( ybot > yll ) ybot = yll ;
622 if( ytop < yhh ) ytop = yhh ;
623 if( yll >= yhh ){ /* shouldn't happen */
624 yhh = yll + 0.05*fabs(yll) + 0.5 ;
625 yll = yll - 0.05*fabs(yll) - 0.5 ;
626 ylo[jj] = yll ; yhi[jj] = yhh ;
627 }
628 }
629 floatfix(ybot) ; floatfix(ytop) ;
630 if( ybot >= ytop ){ /* shouldn't happen */
631 ytop = ybot + 0.05*fabs(ybot) + 0.5 ;
632 ybot = ybot - 0.05*fabs(ybot) - 0.5 ;
633 }
634
635 /* 30 Dec 1998 */
636
637 if( !ysep ){
638 for( jj=0 ; jj < ny ; jj++ ){ ylo[jj] = ybot ; yhi[jj] = ytop ; }
639 }
640
641 /*-- push range of y outwards --*/
642
643 pbot = p10(ybot) ; ptop = p10(ytop) ; if( ptop < pbot ) ptop = pbot ;
644 if( nnayy >= 0 ){
645 nnay = nnayy ;
646 mmay = mmayy ;
647 ybot = yybot ;
648 ytop = yytop ;
649 for( jj=0 ; jj < ny ; jj++ ){ ylo[jj] = ybot ; yhi[jj] = ytop ; }
650 } else if( ptop != 0.0 && ypush > 0 ){
651 np = (ytop-ybot) / ptop ;
652 switch( np ){
653 case 1: ptop *= 0.1 ; break ;
654 case 2: ptop *= 0.2 ; break ;
655 case 3: ptop *= 0.25 ; break ;
656 case 4:
657 case 5: ptop *= 0.5 ; break ;
658 }
659 ybot = floor( ybot/ptop ) * ptop ;
660 ytop = ceil( ytop/ptop ) * ptop ;
661 nnay = floor( (ytop-ybot) / ptop + 0.5 ) ;
662 mmay = (nnay < 3) ? 10
663 : (nnay < 6) ? 5 : 2 ;
664 } else {
665 float dif=(ytop-ybot)*0.005f ;
666 if( ypush == 0 ){ ybot -= dif ; ytop += dif ; }
667 nnay = 1 ; mmay = 10 ;
668 }
669
670 if( nnayy < 0 ){
671 for( jj=0 ; jj < ny ; jj++ ){
672 pbot = p10(ylo[jj]) ; ptop = p10(yhi[jj]) ; if( ptop < pbot ) ptop = pbot ;
673 if( ptop != 0.0 && ypush > 0 ){
674 np = (yhi[jj]-ylo[jj]) / ptop ;
675 switch( np ){
676 case 1: ptop *= 0.1 ; break ;
677 case 2: ptop *= 0.2 ; break ;
678 case 3: ptop *= 0.25 ; break ;
679 case 4:
680 case 5: ptop *= 0.5 ; break ;
681 }
682 ylo[jj] = floor( ylo[jj]/ptop ) * ptop ;
683 yhi[jj] = ceil( yhi[jj]/ptop ) * ptop ;
684 } else if( ypush == 0 ){
685 float dif=(yhi[jj]-ylo[jj])*0.005f ;
686 ylo[jj] -= dif ; yhi[jj] += dif ;
687 }
688 }
689 }
690
691 nnaxx = nnayy = -1 ;
692
693 /*-- setup to plot --*/
694
695 create_memplot_surely( "tsplot" , aspect ) ;
696 set_thick_memplot( thik ) ; /* for labels */
697 #if 0
698 thth = get_opacity_memplot() ;
699 if( thth != 1.0f ) set_opacity_memplot(thth) ;
700 #endif
701
702 /*-- plot labels, if any --*/
703
704 if( xflip ){ xobot = 0.03; xotop = 1.15; } /* set objective size of plot */
705 else { xobot = 0.15; xotop = 1.27; }
706 yobot = 0.1 ; yotop = 0.95 ;
707
708 if( STGOOD(lab_top) ){ yotop -= 0.02 ; yobot -= 0.01 ; }
709 if( nam_yyy != NULL ){
710 if( xflip ){
711 xobot += 0.16 ; xotop += 0.02 ;
712 } else {
713 xotop -= 0.16 ; xobot -= 0.02 ;
714 }
715 }
716
717 if( do_naked ) /* 03 May 2018 */{
718 xobot = yobot = 0.0f ; xotop = 1.3f ;
719 yotop = (STGOOD(lab_top)) ? 0.89 : 0.98 ;
720 }
721
722 /* x-axis label? */
723
724 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
725 if( STGOOD(lab_xxx) )
726 plotpak_pwritf( 0.5*(xobot+xotop), yobot-0.06, lab_xxx, 16, 0, 0 ) ;
727
728 /* y-axis label? */
729
730 if( STGOOD(lab_yyy) ){
731 if( xflip )
732 plotpak_pwritf( xotop+0.10, 0.5*(yobot+yotop), lab_yyy, 16, -90, 0 ) ;
733 else
734 plotpak_pwritf( xobot-0.10, 0.5*(yobot+yotop), lab_yyy, 16, 90, 0 ) ;
735 }
736
737 /* label at top? */
738
739 if( STGOOD(lab_top) && !do_naked ){
740 plotpak_pwritf( xobot , yotop+0.01 , lab_top , 18 , 0 , -2 ) ;
741 }
742
743 /*-- plot all on same vertical scale --*/
744
745 if( yall ){
746 #define ADDTO_SBOX(xv,yv,qq) do{ if( nsbox == asbox ){ \
747 asbox += 64 ; \
748 xsbox = (float *)realloc(xsbox,sizeof(float)*asbox) ; \
749 ysbox = (float *)realloc(ysbox,sizeof(float)*asbox) ; \
750 jsbox = (int * )realloc(jsbox,sizeof(float)*asbox) ; \
751 } \
752 xsbox[nsbox] = (xv); ysbox[nsbox] = (yv); jsbox[nsbox++] = (qq); \
753 } while(0)
754 int do_sbox=0, nsbox=0, asbox=0, *jsbox=NULL ; float *xsbox=NULL, *ysbox=NULL ;
755
756 if( noline && tsbox > 0.0f && ny > 1 ){
757 char *eee = getenv("AFNI_1DPLOT_RANBOX") ;
758 if( eee != NULL && (*eee == 'Y' || *eee == 'y') ) do_sbox = 1 ;
759 }
760
761 /* do name labels at right? */
762
763 if( nam_yyy != NULL ){
764 float yv = yotop ; int sz,yz ;
765
766 for( jj=0 ; jj < ny ; jj++ ){
767 if( STGOOD(nam_yyy[jj]) ){
768 set_color_memplot( ccc[jj%NCLR][0] , ccc[jj%NCLR][1] , ccc[jj%NCLR][2] ) ;
769 set_thick_memplot( 1.234f*THIK ) ;
770 if( use_ddd ) dashno = ddd[jj%NCLR] ;
771 if( use_ddd ) plotpak_setlin(dashno) ;
772 if( xflip )
773 plotpak_line( xobot-0.008 , yv , xobot-0.041 , yv ) ;
774 else
775 plotpak_line( xotop+0.008 , yv , xotop+0.041 , yv ) ;
776 if( use_ddd ) plotpak_setlin(1) ;
777 if( tsbox > 0.0f || dashno == 0 ){
778 set_thick_memplot(thik);
779 if( xflip )
780 { plot_onebox(xobot-0.008,yv,jj ); plot_onebox(xobot-0.041,yv,jj ); }
781 else
782 { plot_onebox(xotop+0.008,yv,jj ); plot_onebox(xotop+0.041,yv,jj ); }
783 }
784 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
785 yz = strlen(nam_yyy[jj]) ;
786 if( yz < 9 ) sz = 11 ;
787 else if( yz < 11 ) sz = 9 ;
788 else if( yz < 13 ) sz = 8 ;
789 else if( yz < 15 ) sz = 7 ;
790 else sz = 6 ;
791 set_thick_memplot( thik*sz/13.9f ) ;
792 if( xflip )
793 plotpak_pwritf( xobot-0.049 , yv , nam_yyy[jj] , sz , 0 , 1 ) ;
794 else
795 plotpak_pwritf( xotop+0.049 , yv , nam_yyy[jj] , sz , 0 , -1 ) ;
796 yv -= 0.05 ;
797 }
798 }
799 }
800
801 /* plot axes */
802
803 floatfix(ybot) ; floatfix(ytop) ;
804 plotpak_set( ASX(xobot),ASX(xotop) , yobot,yotop ,
805 xabot,xatop , ybot,ytop , 1 ) ;
806
807 /* 24 Apr 2012: add vbox stuff now, before other plotting */
808
809 for( iv=0 ; iv < nvbox ; iv++ ){
810 if( vbox[iv].code == VBOX ){
811 set_color_memplot( vbox[iv].rr , vbox[iv].gg , vbox[iv].bb ) ;
812 set_thick_memplot( 0 ) ;
813 xb1 = vbox[iv].x1 ; xb2 = vbox[iv].x2 ;
814 yb1 = ybot ; yb2 = ytop ;
815 zzphys_(&xb1,&yb1); zzphys_(&xb2,&yb2);
816 plotfrect_memplot( xb1,yb1 , xb2,yb2 ) ;
817 } else if( vbox[iv].code == RBOX ){ /* 15 Jun 2017 */
818 float xxb1,yyb1,xxb2,yyb2 ;
819 xb1 = vbox[iv].x1 ; xb2 = vbox[iv].x2 ;
820 yb1 = vbox[iv].rb_y1 ; yb2 = vbox[iv].rb_y2 ;
821 yb3 = vbox[iv].rb_y3 ; /* 05 Sep 2017 */
822
823 set_color_memplot( vbox[iv].rr , vbox[iv].gg , vbox[iv].bb ) ;
824 xxb1 = xb1 ; xxb2 = xb2 ; yyb1 = yb1 ; yyb2 = yb2 ;
825 zzphys_(&xxb1,&yyb1); zzphys_(&xxb2,&yyb2);
826 set_thick_memplot( 0.0f ) ;
827 plotfrect_memplot( xxb1,yyb1 , xxb2,yyb2 ) ;
828
829 set_color_memplot( vbox[iv].rb_rr ,
830 vbox[iv].rb_gg , vbox[iv].rb_bb ) ;
831 set_thick_memplot( 0.0f ) ;
832 plotpak_line( xb1,yb1 , xb1,yb2 ) ;
833 plotpak_line( xb1,yb2 , xb2,yb2 ) ;
834 plotpak_line( xb2,yb2 , xb2,yb1 ) ;
835 plotpak_line( xb2,yb1 , xb1,yb1 ) ;
836 if( (yb3-yb1)*(yb3-yb2) < 0.0f ){ /* 05 Sep 2017 */
837 set_thick_memplot( 0.004f ) ;
838 plotpak_line( xb1,yb3 , xb2,yb3 ) ;
839 }
840 } else if( vbox[iv].code == TLIN ){ /* 19 Sep 2017 */
841 int dc ;
842 xb1 = vbox[iv].x1 ; xb2 = vbox[iv].x2 ;
843 yb1 = vbox[iv].rb_y1 ; yb2 = vbox[iv].rb_y2 ;
844
845 set_color_memplot( vbox[iv].rr , vbox[iv].gg , vbox[iv].bb ) ;
846 set_thick_memplot( 0.004f ) ;
847 dc = vbox[iv].dcode ; if( dc <= 0 ) dc = 1 ; else if( dc > 5 ) dc = 5 ;
848 plotpak_setlin(dc) ;
849 plotpak_line( xb1,yb1 , xb2,yb2 ) ;
850 if( dc != 1 ) plotpak_setlin(1) ; /* solid */
851 }
852 }
853
854 if( do_perim ){
855 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
856 set_thick_memplot( thik ) ;
857 plotpak_perimm( nnax,mmax , nnay,mmay , ilab[(nnax>0)+2*(nnay>0)] ) ;
858 }
859
860 /* plot data */
861
862 for( jj=0 ; jj < ny ; jj++ ){
863 thth = THIK ;
864 if( jj >= thik_n1 && jj <= thik_n2 ) thth = thik_12 ;
865 set_thick_memplot( thth ) ;
866 set_color_memplot( ccc[jj%NCLR][0] , ccc[jj%NCLR][1] , ccc[jj%NCLR][2] ) ;
867 if( use_ddd ) dashno = ddd[jj%NCLR] ;
868
869 if( nsepx > 0 ){
870 int qq = jj ; if( qq >= nsepx ) qq = nsepx-1 ;
871 xx = sepx[qq] ; ixtop = lsepx[qq] ; if( ixtop > nx ) ixtop = nx ;
872 } else {
873 ixtop = nx ;
874 }
875 yy = y[jj] ;
876 if( !noline && dashno != 0 ){
877 if( use_ddd ) plotpak_setlin(dashno) ;
878 if( dohist ){
879 float xp , yb=ybot ;
880 plotpak_line( xx[0],yb , xx[0],yy[0] ) ;
881 for( ii=1 ; ii < ixtop ; ii++ ){
882 plotpak_line( xx[ii-1],yy[ii-1],xx[ii],yy[ii-1]) ;
883 plotpak_line( xx[ii] ,yy[ii-1],xx[ii],yy[ii] ) ;
884 }
885 xp = xx[ixtop-1] + (xx[ixtop-1]-xx[ixtop-2]) ;
886 plotpak_line( xx[ixtop-1],yy[ixtop-1] , xp,yy[ixtop-1] ) ;
887 plotpak_line( xp ,yy[ixtop-1] , xp,yb ) ;
888 } else {
889 for( ii=1 ; ii < ixtop ; ii++ ){
890 #if 0
891 if( fabsf(xx[ii-1]) < WAY_BIG && fabsf(xx[ii]) < WAY_BIG &&
892 fabsf(yy[ii-1]) < WAY_BIG && fabsf(yy[ii]) < WAY_BIG )
893 #else
894 if( xx[ii-1] <= xtop && xx[ii] <= xtop &&
895 yy[ii-1] <= ytop && yy[ii] <= ytop &&
896 xx[ii-1] >= xbot && xx[ii] >= xbot &&
897 yy[ii-1] >= ybot && yy[ii] >= ybot )
898 #endif
899 plotpak_line( xx[ii-1] , yy[ii-1] , xx[ii] , yy[ii] ) ;
900 }
901 }
902 if( use_ddd ) plotpak_setlin(1) ;
903 }
904
905 if( tsbox > 0.0f || dashno == 0 ){
906 if( !do_sbox) set_thick_memplot( thik ) ;
907 for( ii=0 ; ii < ixtop ; ii++ ){
908 if( noline != 2 ||
909 ( xx[ii] >= xbot && xx[ii] <= xtop &&
910 yy[ii] >= ybot && yy[ii] <= ytop ) ){
911 if( do_sbox ) ADDTO_SBOX (xx[ii],yy[ii],jj) ;
912 else plot_onebox(xx[ii],yy[ii],jj) ;
913 }
914 }
915 set_thick_memplot( THIK ) ;
916 }
917 } /* end of loop over different curve to plot */
918
919 if( do_sbox && nsbox > 0 ){ /* 24 Oct 2013 */
920 int qq , ss , ds ;
921 set_thick_memplot( thik ) ;
922 ds = (4*nsbox)/5 ;
923 for( qq=0 ; qq < ds ; qq++ ){
924 ss = lrand48() % nsbox ; jj = jsbox[ss] ; if( jj < 0 ) continue ;
925 set_color_memplot( ccc[jj%NCLR][0] , ccc[jj%NCLR][1] , ccc[jj%NCLR][2] ) ;
926 plot_onebox(xsbox[ss],ysbox[ss],jj) ; jsbox[ss] = -1 ;
927 }
928 ds = ts_find_relprime(nsbox) ;
929 for( qq=0,ss=nsbox/7 ; qq < nsbox ; qq++,ss=(ss+ds)%nsbox ){
930 jj = jsbox[ss] ; if( jj < 0 ) continue ;
931 set_color_memplot( ccc[jj%NCLR][0] , ccc[jj%NCLR][1] , ccc[jj%NCLR][2] ) ;
932 plot_onebox(xsbox[ss],ysbox[ss],jj) ; jsbox[ss] = -1 ;
933 }
934 free(jsbox) ; free(ysbox) ; free(xsbox) ;
935 }
936
937 set_thick_memplot( thik ) ;
938 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
939
940 } else { /*-- plot each on separate vertical scale --*/
941
942 float dyo = (yotop-yobot) / ( (1.0+SY) * ny - SY ) ;
943
944 /* name labels at right? */
945
946 if( nam_yyy != NULL ){
947 float yv = yotop ; int sz,yz ;
948
949 for( jj=0 ; jj < ny ; jj++ ){
950 yll = yobot + jj*(1.0+SY)*dyo ; yhh = yll + dyo ;
951 if( STGOOD(nam_yyy[jj]) ){
952 set_color_memplot( ccc[jj%NCLR][0] , ccc[jj%NCLR][1] , ccc[jj%NCLR][2] ) ;
953 set_thick_memplot( 1.234f*THIK ) ;
954 yv = 0.7*yhh + 0.3*yll ;
955 if( use_ddd ) dashno = ddd[jj%NCLR] ;
956 if( use_ddd ) plotpak_setlin(dashno) ;
957 if( xflip )
958 plotpak_line( xobot-0.008 , yv , xobot-0.041 , yv ) ;
959 else
960 plotpak_line( xotop+0.008 , yv , xotop+0.041 , yv ) ;
961 if( use_ddd ) plotpak_setlin(1) ;
962 if( tsbox > 0.0f || dashno == 0 ){
963 set_thick_memplot(thik);
964 if( xflip )
965 { plot_onebox(xobot-0.008,yv,jj ); plot_onebox(xobot-0.041,yv,jj ); }
966 else
967 { plot_onebox(xotop+0.008,yv,jj ); plot_onebox(xotop+0.041,yv,jj ); }
968 }
969 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
970 yz = strlen(nam_yyy[jj]) ;
971 if( yz < 9 ) sz = 11 ;
972 else if( yz < 11 ) sz = 9 ;
973 else if( yz < 13 ) sz = 8 ;
974 else if( yz < 15 ) sz = 7 ;
975 else sz = 6 ;
976 set_thick_memplot( thik*sz/13.9f ) ;
977 if( xflip )
978 plotpak_pwritf( xobot-0.049 , yv , nam_yyy[jj] , sz , 0 , 1 ) ;
979 else
980 plotpak_pwritf( xotop+0.049 , yv , nam_yyy[jj] , sz , 0 , -1 ) ;
981 }
982 }
983 }
984
985 /* data each in its own box */
986
987 if( ny > 19 ) plotpak_labmod( 0 , 5 ) ; /* 09 Dec 2010 */
988 else if( ny > 9 ) plotpak_labmod( 0 , 7 ) ;
989
990 for( jj=ny-1 ; jj >= 0 ; jj-- ){
991 yll = yobot + jj*(1.0+SY)*dyo ; yhh = yll + dyo ;
992 floatfix(ylo[jj]) ; floatfix(yhi[jj]) ;
993 plotpak_set( ASX(xobot),ASX(xotop) , yll,yhh ,
994 xabot,xatop , ylo[jj],yhi[jj] , 1 ) ;
995
996 /* 24 Apr 2012: add vbox stuff now, before other plotting */
997
998 set_thick_memplot(0.0f) ;
999 for( iv=0 ; iv < nvbox ; iv++ ){
1000 if( vbox[iv].ygr == jj || vbox[iv].ygr < 0 ){
1001 if( vbox[iv].code == VBOX ){
1002 set_color_memplot( vbox[iv].rr , vbox[iv].gg , vbox[iv].bb ) ;
1003 xb1 = vbox[iv].x1 ; xb2 = vbox[iv].x2 ;
1004 yb1 = ylo[jj] ; yb2 = yhi[jj] ;
1005 zzphys_(&xb1,&yb1); zzphys_(&xb2,&yb2);
1006 plotfrect_memplot( xb1,yb1 , xb2,yb2 );
1007 }
1008 }
1009 }
1010
1011 if( nnay > 0 ){
1012 nnay = 1 ;
1013 pbot = p10(ylo[jj]) ; ptop = p10(yhi[jj]) ;
1014 if( ptop > pbot && pbot > 0.0 ) ptop = pbot ;
1015 if( ptop != 0.0 ) mmay = floor( (yhi[jj]-ylo[jj]) / ptop + 0.5 ) ;
1016 else mmay = 5 ; /* shouldn't happen */
1017
1018 if( mmay == 1 ) mmay = 5 ;
1019 else if( mmay == 2 ) mmay = 4 ;
1020 else if( mmay == 3 ) mmay = 6 ;
1021 }
1022
1023 if( do_perim ){
1024 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1025 plotpak_perimm( nnax,mmax , nnay,mmay , ilab[(nnax>0)*(jj==0)+2*(nnay>0)] ) ;
1026 }
1027 if( ylo[jj] < 0.0 && yhi[jj] > 0.0 ){
1028 set_thick_memplot( 0.0 ) ;
1029 plotpak_setlin(3) ;
1030 plotpak_line( xbot,0.0 , xtop,0.0 ) ;
1031 plotpak_setlin(1) ;
1032 }
1033
1034 set_color_memplot( ccc[jj%NCLR][0] , ccc[jj%NCLR][1] , ccc[jj%NCLR][2] ) ;
1035 thth = THIK ;
1036 if( jj >= thik_n1 && jj <= thik_n2 ) thth = thik_12 ;
1037 set_thick_memplot( thth ) ;
1038
1039 if( nsepx > 0 ){
1040 int qq = jj ; if( qq >= nsepx ) qq = nsepx-1 ;
1041 xx = sepx[qq] ; ixtop = lsepx[qq] ; if( ixtop > nx ) ixtop = nx ;
1042 } else {
1043 ixtop = nx ;
1044 }
1045 yy = y[jj] ;
1046 if( use_ddd ) dashno = ddd[jj%NCLR] ;
1047 if( !noline && dashno != 0 ){
1048 if( use_ddd ) plotpak_setlin(dashno) ;
1049 if( dohist ){
1050 float xp , yb=ylo[jj] ;
1051 plotpak_line( xx[0],yb , xx[0],yy[0] ) ;
1052 for( ii=1 ; ii < ixtop ; ii++ ){
1053 plotpak_line( xx[ii-1],yy[ii-1],xx[ii],yy[ii-1]) ;
1054 plotpak_line( xx[ii] ,yy[ii-1],xx[ii],yy[ii] ) ;
1055 }
1056 xp = xx[ixtop-1] + (xx[ixtop-1]-xx[ixtop-2]) ;
1057 plotpak_line( xx[ixtop-1],yy[ixtop-1] , xp,yy[ixtop-1] ) ;
1058 plotpak_line( xp ,yy[ixtop-1] , xp,yb ) ;
1059 } else {
1060 for( ii=1 ; ii < ixtop ; ii++ ){
1061 #if 0
1062 if( fabsf(xx[ii-1]) < WAY_BIG && fabsf(xx[ii]) < WAY_BIG &&
1063 fabsf(yy[ii-1]) < WAY_BIG && fabsf(yy[ii]) < WAY_BIG )
1064 #else
1065 if( xx[ii-1] <= xtop && xx[ii] <= xtop &&
1066 yy[ii-1] <= yhi[jj] && yy[ii] <= yhi[jj] &&
1067 xx[ii-1] >= xbot && xx[ii] >= xbot &&
1068 yy[ii-1] >= ylo[jj] && yy[ii] >= ylo[jj] )
1069 #endif
1070 plotpak_line( xx[ii-1] , yy[ii-1] , xx[ii] , yy[ii] ) ;
1071 }
1072 }
1073 set_thick_memplot( thik ) ;
1074 if( use_ddd ) plotpak_setlin(1) ;
1075 }
1076
1077 if( tsbox > 0.0f || dashno == 0 ){
1078 for( ii=0 ; ii < ixtop ; ii++ ){
1079 if( noline != 2 ||
1080 ( xx[ii] >= xbot && xx[ii] <= xtop &&
1081 yy[ii] >= ylo[jj] && yy[ii] <= yhi[jj] ) )
1082 plot_onebox( xx[ii] , yy[ii] , jj ) ;
1083 }
1084 }
1085
1086 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1087 }
1088 }
1089
1090 if( STGOOD(lab_top) && do_naked ){
1091 plotpak_pwritf_phys( xobot+0.05 , yotop+0.02 , lab_top , 18 , 0 , -1 ) ;
1092 }
1093
1094 /*-- exit, stage left --*/
1095
1096 set_thick_memplot( 0.0 ) ;
1097 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1098 plot_ts_clear_vbox() ;
1099
1100 if( nsepx == 0 && xx != x ) free(xx) ;
1101 free(ylo) ; free(yhi) ;
1102
1103 mp = get_active_memplot() ;
1104 return mp ;
1105 }
1106
1107 /*-----------------------------------------------------------------------
1108 Plot some timeseries data into window (linear-linear scales).
1109 If array x[] is NULL, then routine will make an x-axis up.
1110 If nx < 0, this is a flag to scale each y[i][] array separately
1111 If ny < 0, this is a flag to plot each y[i][] array into a separate
1112 graph; ny > 0 means all in one graph.
1113 -------------------------------------------------------------------------*/
1114
plot_ts_lab(Display * dpy,int nx,float * x,int ny,float ** y,char * lab_xxx,char * lab_yyy,char * lab_top,char ** nam_yyy,void_func * killfunc)1115 void plot_ts_lab( Display * dpy ,
1116 int nx , float * x , int ny , float ** y ,
1117 char * lab_xxx , char * lab_yyy , char * lab_top ,
1118 char ** nam_yyy , void_func * killfunc )
1119 {
1120 MEM_plotdata * mp ;
1121 int ymask = 0 ;
1122
1123 if( dpy == NULL ) return ;
1124
1125 if (nx < 0 ){ ymask = ymask | TSP_SEPARATE_YSCALE; nx = -nx; }
1126 if( ny < 0 ){ ymask = ymask | TSP_SEPARATE_YBOX ; ny = -ny ; }
1127
1128 mp = plot_ts_mem( nx,x , ny,ymask,y , lab_xxx , lab_yyy , lab_top , nam_yyy ) ;
1129 if( mp != NULL )
1130 (void) memplot_to_topshell( dpy , mp , killfunc ) ;
1131
1132 return ;
1133 }
1134
1135 /*----------------------------------------------------------------------
1136 Return p10 as a power of 10 such that
1137 p10 <= fabs(x) < 10*p10
1138 unless x == 0, in which case return 0.
1139 ------------------------------------------------------------------------*/
1140
p10(float x)1141 static float p10( float x )
1142 {
1143 double y ;
1144
1145 if( x == 0.0 ) return 0.0 ;
1146 if( x < 0.0 ) x = -x ;
1147 y = floor(log10(x)+0.000001) ; y = pow( 10.0 , y ) ;
1148 return (float) y ;
1149 }
1150
1151 /*----------------------------------------------------------------------*/
1152
plot_ts_init(Display * dpy,float xbot,float xtop,int ny,float ybot,float ytop,char * lab_xxx,char * lab_yyy,char * lab_top,char ** nam_yyy,void_func * killfunc)1153 MEM_topshell_data * plot_ts_init( Display * dpy ,
1154 float xbot , float xtop ,
1155 int ny , float ybot , float ytop ,
1156 char * lab_xxx , char * lab_yyy ,
1157 char * lab_top , char ** nam_yyy ,
1158 void_func * killfunc )
1159 {
1160 int ii , jj , np , nnax,nnay , mmax,mmay , yall ;
1161 float pbot,ptop , xobot,xotop,yobot,yotop , yll,yhh ;
1162 char str[32] ;
1163 float * ud ;
1164 MEM_topshell_data * mp ;
1165
1166 /*-- sanity check --*/
1167
1168 if( dpy == NULL || ny == 0 || xbot >= xtop || ybot >= ytop ) return NULL ;
1169
1170 init_colors() ;
1171
1172 if( do_naked ){ /* 03 May 2018 */
1173 lab_xxx = lab_yyy = NULL ; nam_yyy = NULL ;
1174 }
1175 if( do_naked > 1 ){
1176 lab_top = NULL ;
1177 }
1178
1179 /*-- push range of x outwards --*/
1180
1181 pbot = p10(xbot) ; ptop = p10(xtop) ; if( ptop < pbot ) ptop = pbot ;
1182 if( ptop != 0.0 && xpush > 0 ){
1183 np = (xtop-xbot) / ptop ;
1184 switch( np ){
1185 case 1: ptop *= 0.1 ; break ;
1186 case 2: ptop *= 0.2 ; break ;
1187 case 3: ptop *= 0.25 ; break ;
1188 case 4:
1189 case 5: ptop *= 0.5 ; break ;
1190 }
1191 xbot = floor( xbot/ptop ) * ptop ;
1192 xtop = ceil( xtop/ptop ) * ptop ;
1193 nnax = floor( (xtop-xbot) / ptop + 0.5 ) ;
1194 mmax = (nnax < 3) ? 10
1195 : (nnax < 6) ? 5 : 2 ;
1196 } else {
1197 nnax = 1 ; mmax = 10 ;
1198 ii = (int)rint(xtop-xbot) ;
1199 if( fabs(xtop-xbot-ii) < 0.01 && ii <= 200 ) mmax = ii ;
1200 }
1201
1202 /*-- push range of y outwards --*/
1203
1204 yall = (ny > 0) ; if( !yall ) ny = -ny ;
1205
1206 pbot = p10(ybot) ; ptop = p10(ytop) ; if( ptop < pbot ) ptop = pbot ;
1207 if( ptop != 0.0 && ypush > 0){
1208 np = (ytop-ybot) / ptop ;
1209 switch( np ){
1210 case 1: ptop *= 0.1 ; break ;
1211 case 2: ptop *= 0.2 ; break ;
1212 case 3: ptop *= 0.25 ; break ;
1213 case 4:
1214 case 5: ptop *= 0.5 ; break ;
1215 }
1216 ybot = floor( ybot/ptop ) * ptop ;
1217 ytop = ceil( ytop/ptop ) * ptop ;
1218 nnay = floor( (ytop-ybot) / ptop + 0.5 ) ;
1219 mmay = (nnay < 3) ? 10
1220 : (nnay < 6) ? 5 : 2 ;
1221 } else {
1222 float dif=(ytop-ybot)*0.005f ;
1223 if( ypush == 0 ){ ybot -= dif ; ytop += dif ; }
1224 nnay = 1 ; mmay = 10 ;
1225 }
1226
1227 /*-- setup to plot --*/
1228
1229 create_memplot_surely( "Tsplot" , aspect ) ;
1230 set_thick_memplot( thik*1.5f ) ;
1231
1232 /*-- plot labels, if any --*/
1233
1234 xobot = 0.15 ; xotop = 1.27 ; /* set objective size of plot */
1235 yobot = 0.1 ; yotop = 0.95 ;
1236
1237 if( STGOOD(lab_top) ){ yotop -= 0.02 ; yobot -= 0.01 ; }
1238 if( nam_yyy != NULL ){ xotop -= 0.16 ; xobot -= 0.02 ; }
1239
1240 if( do_naked ) /* 03 May 2018 */{
1241 xobot = yobot = 0.0f ; xotop = 1.3f ;
1242 yotop = (STGOOD(lab_top)) ? 0.89 : 0.98 ;
1243 }
1244
1245 /* x-axis label? */
1246
1247 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1248 if( STGOOD(lab_xxx) )
1249 plotpak_pwritf( 0.5*(xobot+xotop) , yobot-0.06 , lab_xxx , 16 , 0 , 0 ) ;
1250
1251 /* y-axis label? */
1252
1253 if( STGOOD(lab_yyy) )
1254 plotpak_pwritf( xobot-0.10 , 0.5*(yobot+yotop) , lab_yyy , 16 , 90 , 0 ) ;
1255
1256 /* label at top? */
1257
1258 if( STGOOD(lab_top) && !do_naked ){
1259 plotpak_pwritf( xobot , yotop+0.01 , lab_top , 18 , 0 , -2 ) ;
1260 }
1261
1262 /*-- plot all on same vertical scale --*/
1263
1264 ud = (float *) malloc( sizeof(float) * 8 ) ;
1265 ud[0] = xobot ; ud[1] = xotop ; ud[2] = yobot ; ud[3] = yotop ;
1266 ud[4] = xbot ; ud[5] = xtop ; ud[6] = ybot ; ud[7] = ytop ;
1267
1268 if( yall ){
1269
1270 /* do name labels at right? */
1271
1272 if( nam_yyy != NULL ){
1273 float yv = yotop ; int sz ;
1274
1275 for( jj=0 ; jj < ny ; jj++ ){
1276 if( STGOOD(nam_yyy[jj]) ){
1277 set_color_memplot( ccc[jj%NCLR][0] , ccc[jj%NCLR][1] , ccc[jj%NCLR][2] ) ;
1278 set_thick_memplot( 1.234f*THIK ) ;
1279 plotpak_line( xotop+0.008 , yv , xotop+0.042 , yv ) ;
1280 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1281 sz = (strlen(nam_yyy[jj]) <= 10) ? 12 : 9 ;
1282 set_thick_memplot( thik*sz/13.9f ) ;
1283 plotpak_pwritf( xotop+0.048 , yv , nam_yyy[jj] , sz , 0 , -1 ) ;
1284 yv -= 0.05 ;
1285 }
1286 }
1287 }
1288
1289 /* plot axes */
1290
1291 floatfix(ybot) ; floatfix(ytop) ;
1292 plotpak_set( ASX(xobot),ASX(xotop) , yobot,yotop ,
1293 xbot,xtop , ybot,ytop , 1 ) ;
1294 if( do_perim ){
1295 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1296 plotpak_perimm( nnax,mmax , nnay,mmay , ilab[(nnax>0)+2*(nnay>0)] ) ;
1297 }
1298
1299 } else { /*-- plot each on separate vertical scale --*/
1300
1301 float dyo = (yotop-yobot) / ( (1.0+SY) * ny - SY ) ;
1302
1303 /* name labels at right? */
1304
1305 if( nam_yyy != NULL ){
1306 float yv = yotop ; int sz ;
1307
1308 for( jj=0 ; jj < ny ; jj++ ){
1309 yll = yobot + jj*(1.0+SY)*dyo ; yhh = yll + dyo ;
1310 if( STGOOD(nam_yyy[jj]) ){
1311 set_color_memplot( ccc[jj%NCLR][0] , ccc[jj%NCLR][1] , ccc[jj%NCLR][2] ) ;
1312 set_thick_memplot( 1.234f*THIK ) ;
1313 yv = 0.7*yhh + 0.3*yll ;
1314 plotpak_line( xotop+0.008 , yv , xotop+0.042 , yv ) ;
1315 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1316 sz = (strlen(nam_yyy[jj]) <= 10) ? 12 : 9 ;
1317 set_thick_memplot( thik*sz/13.9f ) ;
1318 plotpak_pwritf( xotop+0.048 , yv , nam_yyy[jj] , sz , 0 , -1 ) ;
1319 }
1320 }
1321 }
1322
1323 /* data each in its own box */
1324
1325 nnay = 1 ;
1326 pbot = p10(ybot) ; ptop = p10(ytop) ;
1327 if( ptop > pbot && pbot > 0.0 ) ptop = pbot ;
1328 if( ptop != 0.0 ) mmay = floor( (ytop-ybot) / ptop + 0.5 ) ;
1329 else mmay = 5 ; /* shouldn't happen */
1330
1331 if( mmay == 1 ) mmay = 5 ;
1332 else if( mmay == 2 ) mmay = 4 ;
1333 else if( mmay == 3 ) mmay = 6 ;
1334
1335 for( jj=ny-1 ; jj >= 0 ; jj-- ){
1336 yll = yobot + jj*(1.0+SY)*dyo ; yhh = yll + dyo ;
1337 floatfix(ybot) ; floatfix(ytop) ;
1338 plotpak_set( ASX(xobot),ASX(xotop) , yll,yhh ,
1339 xbot,xtop , ybot,ytop , 1 ) ;
1340 if( do_perim ){
1341 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1342 plotpak_perimm( nnax,mmax , nnay,mmay , ilab[(nnax>0)*(jj==0)+2*(nnay>0)] ) ;
1343 }
1344 if( ybot < 0.0 && ytop > 0.0 ){
1345 plotpak_setlin(5) ;
1346 plotpak_line( xbot,0.0 , xtop,0.0 ) ;
1347 plotpak_setlin(1) ;
1348 }
1349 }
1350 }
1351
1352 if( STGOOD(lab_top) && do_naked ){
1353 plotpak_pwritf_phys( xobot+0.05 , yotop+0.02 , lab_top , 18 , 0 , -1 ) ;
1354 }
1355
1356 /*-- display --*/
1357
1358 mp = memplot_to_topshell( dpy , get_active_memplot() , killfunc ) ;
1359 if( mp == NULL ){ free(ud) ; return NULL; }
1360 mp->userdata = ud ;
1361
1362 /*-- exit, stage left --*/
1363
1364 return mp ;
1365 }
1366
1367 /*----------------------------------------------------------------------*/
1368
plot_ts_addto(MEM_topshell_data * mp,int nx,float * x,int ny,float ** y)1369 void plot_ts_addto( MEM_topshell_data * mp ,
1370 int nx , float * x , int ny , float ** y )
1371 {
1372 int ii , jj , yall , start ;
1373 float pbot,ptop , xobot,xotop,yobot,yotop , yll,yhh ;
1374 float xbot,xtop , ybot,ytop ;
1375 float * yy , * xx ;
1376 float * ud ;
1377
1378 if( mp == NULL || mp->userdata == NULL || ! mp->valid ||
1379 nx <= 1 || ny == 0 || x == NULL || y == NULL ) return ;
1380
1381 init_colors() ;
1382
1383 ud = (float *) mp->userdata ;
1384 xobot = ud[0] ; xotop = ud[1] ; yobot = ud[2] ; yotop = ud[3] ;
1385 xbot = ud[4] ; xtop = ud[5] ; ybot = ud[6] ; ytop = ud[7] ;
1386
1387 yall = (ny > 0) ; if( !yall ) ny = -ny ;
1388
1389 ii = set_active_memplot( MEMPLOT_IDENT(mp->mp) ) ;
1390 if( ii != 0 ) return ;
1391
1392 start = MEMPLOT_NLINE(mp->mp) ;
1393 xx = x ;
1394
1395 if( yall ){ /*-- all in one big happy box --*/
1396
1397 floatfix(ybot) ; floatfix(ytop) ;
1398 plotpak_set( ASX(xobot),ASX(xotop) , yobot,yotop ,
1399 xbot,xtop , ybot,ytop , 1 ) ;
1400 set_thick_memplot( THIK ) ;
1401
1402 /* plot data */
1403
1404 for( jj=0 ; jj < ny ; jj++ ){
1405 set_color_memplot( ccc[jj%NCLR][0] , ccc[jj%NCLR][1] , ccc[jj%NCLR][2] ) ;
1406
1407 yy = y[jj] ;
1408 for( ii=1 ; ii < nx ; ii++ ){
1409 if( fabsf(xx[ii-1]) < WAY_BIG && fabsf(xx[ii]) < WAY_BIG &&
1410 fabsf(yy[ii-1]) < WAY_BIG && fabsf(yy[ii]) < WAY_BIG )
1411
1412 plotpak_line( xx[ii-1] , yy[ii-1] , xx[ii] , yy[ii] ) ;
1413 }
1414 }
1415 set_thick_memplot( 0.0 ) ;
1416 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1417
1418 } else { /*-- each in its own little sad box --*/
1419
1420 float dyo = (yotop-yobot) / ( (1.0+SY) * ny - SY ) ;
1421
1422 set_thick_memplot( THIK ) ;
1423
1424 for( jj=ny-1 ; jj >= 0 ; jj-- ){
1425 yll = yobot + jj*(1.0+SY)*dyo ; yhh = yll + dyo ;
1426 floatfix(ybot) ; floatfix(ytop) ;
1427 plotpak_set( ASX(xobot),ASX(xotop) , yll,yhh ,
1428 xbot,xtop , ybot,ytop , 1 ) ;
1429 set_color_memplot( ccc[jj%NCLR][0] , ccc[jj%NCLR][1] , ccc[jj%NCLR][2] ) ;
1430
1431 yy = y[jj] ;
1432 for( ii=1 ; ii < nx ; ii++ ){
1433 if( fabsf(xx[ii-1]) < WAY_BIG && fabsf(xx[ii]) < WAY_BIG &&
1434 fabsf(yy[ii-1]) < WAY_BIG && fabsf(yy[ii]) < WAY_BIG )
1435
1436 plotpak_line( xx[ii-1] , yy[ii-1] , xx[ii] , yy[ii] ) ;
1437 }
1438 }
1439 set_thick_memplot( 0.0 ) ;
1440 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1441 }
1442
1443 memplot_to_X11_sef( XtDisplay(mp->drawing) , XtWindow(mp->drawing) ,
1444 mp->mp , start,0,MEMPLOT_FREE_ASPECT ) ;
1445
1446 return ;
1447 }
1448
1449 /*-----------------------------------------------------------------------
1450 Plot a timeseries with error bars, into an in-memory plot structure.
1451 If array x[] is NULL, then routine will make an x-axis up.
1452 -------------------------------------------------------------------------*/
1453
plot_ts_ebar(int nx,float * x,float * y,float * ey,char * lab_xxx,char * lab_yyy,char * lab_top)1454 MEM_plotdata * plot_ts_ebar( int nx , float *x , float *y , float *ey ,
1455 char *lab_xxx , char *lab_yyy , char *lab_top )
1456 {
1457 int ii , jj , np , nnax,nnay , mmax,mmay ;
1458 float *xx ;
1459 float xbot,xtop , ybot,ytop , pbot,ptop , xobot,xotop,yobot,yotop ;
1460 char str[32] ;
1461 MEM_plotdata *mp ;
1462 float ymm , ypp , xmm,xpp,xdd ;
1463
1464 /*-- sanity check --*/
1465
1466 if( nx <= 1 || y == NULL || ey == NULL ) return NULL ;
1467
1468 init_colors() ;
1469
1470 /*-- make up an x-axis if none given --*/
1471
1472 if( x == NULL ){
1473 xx = (float *) malloc( sizeof(float) * nx ) ;
1474 for( ii=0 ; ii < nx ; ii++ ) xx[ii] = ii ;
1475 xbot = 0 ; xtop = nx-1 ;
1476 } else {
1477 xx = x ;
1478 xbot = WAY_BIG ; xtop = -WAY_BIG ;
1479 for( ii=0 ; ii < nx ; ii++ ){
1480 if( xx[ii] < xbot && fabsf(xx[ii]) < WAY_BIG ) xbot = xx[ii] ;
1481 if( xx[ii] > xtop && fabsf(xx[ii]) < WAY_BIG ) xtop = xx[ii] ;
1482 }
1483 if( xbot >= xtop ) return NULL ;
1484 }
1485
1486 /*-- push range of x outwards --*/
1487
1488 pbot = p10(xbot) ; ptop = p10(xtop) ; if( ptop < pbot ) ptop = pbot ;
1489 if( nnaxx >= 0 ){
1490 nnax = nnaxx ;
1491 mmax = mmaxx ;
1492 xbot = xxbot ;
1493 xtop = xxtop ;
1494 } else if( ptop != 0.0 && xpush > 0 ){
1495 np = (xtop-xbot) / ptop ;
1496 switch( np ){
1497 case 1: ptop *= 0.1 ; break ;
1498 case 2: ptop *= 0.2 ; break ;
1499 case 3: ptop *= 0.25 ; break ;
1500 case 4:
1501 case 5: ptop *= 0.5 ; break ;
1502 }
1503 xbot = floor( xbot/ptop ) * ptop ;
1504 xtop = ceil( xtop/ptop ) * ptop ;
1505 nnax = floor( (xtop-xbot) / ptop + 0.5 ) ;
1506 mmax = (nnax < 3) ? 10
1507 : (nnax < 6) ? 5 : 2 ;
1508 } else {
1509 nnax = 1 ; mmax = 10 ;
1510 ii = (int)rint(xtop-xbot) ;
1511 if( fabs(xtop-xbot-ii) < 0.01 && ii <= 200 ) mmax = ii ;
1512 }
1513
1514 /*-- find range of y --*/
1515
1516 ybot = WAY_BIG ; ytop = -WAY_BIG ;
1517 for( ii=0 ; ii < nx ; ii++ ){
1518 if( y[ii] < ybot ) ybot = y[ii] ;
1519 if( y[ii] > ytop ) ytop = y[ii] ;
1520 }
1521 floatfix(ybot) ; floatfix(ytop) ;
1522 if( ybot >= ytop ){ /* shouldn't happen */
1523 ytop = ybot + 0.05f*fabsf(ybot) + 0.1f ;
1524 ybot = ybot - 0.05f*fabsf(ybot) - 0.1f ;
1525 }
1526
1527 /*-- push range of y outwards --*/
1528
1529 pbot = p10(ybot) ; ptop = p10(ytop) ; if( ptop < pbot ) ptop = pbot ;
1530 if( nnayy >= 0 ){
1531 nnay = nnayy ;
1532 mmay = mmayy ;
1533 ybot = yybot ;
1534 ytop = yytop ;
1535 } else if( ptop != 0.0 && ypush > 0 ){
1536 np = (ytop-ybot) / ptop ;
1537 switch( np ){
1538 case 1: ptop *= 0.1 ; break ;
1539 case 2: ptop *= 0.2 ; break ;
1540 case 3: ptop *= 0.25 ; break ;
1541 case 4:
1542 case 5: ptop *= 0.5 ; break ;
1543 }
1544 ybot = floor( ybot/ptop ) * ptop ;
1545 ytop = ceil( ytop/ptop ) * ptop ;
1546 nnay = floor( (ytop-ybot) / ptop + 0.5 ) ;
1547 mmay = (nnay < 3) ? 10
1548 : (nnay < 6) ? 5 : 2 ;
1549 } else {
1550 float dif=(ytop-ybot)*0.005f ;
1551 if( ypush == 0 ){ ybot -= dif ; ytop += dif ; }
1552 nnay = 1 ; mmay = 10 ;
1553 }
1554
1555 if( nnayy < 0 ){
1556 pbot = p10(ybot) ; ptop = p10(ytop) ; if( ptop < pbot ) ptop = pbot ;
1557 if( ptop != 0.0 && ypush > 0 ){
1558 np = (ytop-ybot) / ptop ;
1559 switch( np ){
1560 case 1: ptop *= 0.1 ; break ;
1561 case 2: ptop *= 0.2 ; break ;
1562 case 3: ptop *= 0.25 ; break ;
1563 case 4:
1564 case 5: ptop *= 0.5 ; break ;
1565 }
1566 ybot = floor( ybot/ptop ) * ptop ;
1567 ytop = ceil( ytop/ptop ) * ptop ;
1568 } else if( ypush == 0 ){
1569 float dif=(ytop-ybot)*0.005f ;
1570 ybot -= dif ; ytop += dif ;
1571 }
1572 }
1573
1574 nnaxx = nnayy = -1 ;
1575
1576 /*-- setup to plot --*/
1577
1578 create_memplot_surely( "tsplot" , aspect ) ;
1579 set_thick_memplot( thik ) ; /* for labels */
1580
1581 /*-- plot labels, if any --*/
1582
1583 xobot = 0.15 ; xotop = 1.27 ; /* set objective size of plot */
1584 yobot = 0.1 ; yotop = 0.95 ;
1585
1586 if( STGOOD(lab_top) ){ yotop -= 0.02 ; yobot -= 0.01 ; }
1587
1588 /* x-axis label? */
1589
1590 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1591 if( STGOOD(lab_xxx) )
1592 plotpak_pwritf( 0.5*(xobot+xotop) , yobot-0.06 , lab_xxx , 16 , 0 , 0 ) ;
1593
1594 /* y-axis label? */
1595
1596 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1597 if( STGOOD(lab_yyy) )
1598 plotpak_pwritf( xobot-0.10 , 0.5*(yobot+yotop) , lab_yyy , 16 , 90 , 0 ) ;
1599
1600 /* label at top? */
1601
1602 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1603 if( STGOOD(lab_top) )
1604 plotpak_pwritf( xobot+0.01 , yotop+0.01 , lab_top , 18 , 0 , -2 ) ;
1605
1606 /*-- start plotting --*/
1607
1608 /* plot axes */
1609
1610 floatfix(ybot) ; floatfix(ytop) ;
1611 plotpak_set( ASX(xobot),ASX(xotop) , yobot,yotop ,
1612 xbot,xtop , ybot,ytop , 1 ) ;
1613 if( do_perim ){
1614 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1615 set_thick_memplot( thik ) ;
1616 plotpak_perimm( nnax,mmax , nnay,mmay , ilab[(nnax>0)+2*(nnay>0)] ) ;
1617 }
1618
1619 xdd = (xtop-xbot)*0.00333f ;
1620
1621 /* plot data */
1622
1623 set_thick_memplot( THIK ) ;
1624 set_color_memplot( ccc[0][0] , ccc[0][1] , ccc[0][2] ) ;
1625
1626 for( ii=1 ; ii < nx ; ii++ ){
1627 if( fabsf(xx[ii-1]) < WAY_BIG && fabsf(xx[ii]) < WAY_BIG &&
1628 fabsf(y [ii-1]) < WAY_BIG && fabsf(y [ii]) < WAY_BIG )
1629 plotpak_line( xx[ii-1] , y[ii-1] , xx[ii] , y[ii] ) ;
1630 }
1631
1632 set_thick_memplot( 0.0 ) ;
1633 set_color_memplot( ccc[1][0] , ccc[1][1] , ccc[1][2] ) ;
1634 for( ii=0 ; ii < nx ; ii++ ){
1635 if( fabsf(xx[ii]) < WAY_BIG && fabsf(y [ii]) < WAY_BIG &&
1636 fabsf(ey[ii]) < WAY_BIG && ey[ii] != 0.0 ){
1637
1638 ymm = y[ii] - ey[ii] ; ypp = y[ii] + ey[ii] ;
1639 xmm = xx[ii] - xdd ; xpp = xx[ii] + xdd ;
1640
1641 plotpak_line( xmm,ymm , xpp,ymm ) ;
1642 plotpak_line( xmm,ypp , xpp,ypp ) ;
1643 if( nx <= 333 )
1644 plotpak_line( xx[ii],ymm , xx[ii],ypp ) ;
1645 }
1646 }
1647
1648 /*-- exit, stage left --*/
1649
1650 set_color_memplot( 0.0 , 0.0 , 0.0 ) ;
1651 if( xx != x ) free(xx) ;
1652 mp = get_active_memplot() ;
1653 return mp ;
1654 }
1655
1656 /*-----------------------------------------------------------------------*/
1657
plot_ts_ebar_win(Display * dpy,int nx,float * x,float * y,float * ey,char * lab_xxx,char * lab_yyy,char * lab_top,void_func * killfunc)1658 void plot_ts_ebar_win( Display *dpy ,
1659 int nx , float *x , float *y , float *ey ,
1660 char *lab_xxx , char *lab_yyy , char *lab_top ,
1661 void_func *killfunc )
1662 {
1663 MEM_plotdata *mp ;
1664 mp = plot_ts_ebar( nx,x,y,ey,lab_xxx,lab_yyy,lab_top ) ;
1665 if( mp != NULL )
1666 (void) memplot_to_topshell( dpy , mp , killfunc ) ;
1667 }
1668