Actual source code: axisc.c
petsc-3.4.5 2014-06-29
1: #include <../src/sys/classes/draw/utils/axisimpl.h> /*I "petscdraw.h" I*/
3: PetscClassId PETSC_DRAWAXIS_CLASSID = 0;
7: /*@
8: PetscDrawAxisCreate - Generate the axis data structure.
10: Collective over PetscDraw
12: Input Parameters:
13: . win - PetscDraw object where axis to to be made
15: Ouput Parameters:
16: . axis - the axis datastructure
18: Level: advanced
20: @*/
21: PetscErrorCode PetscDrawAxisCreate(PetscDraw draw,PetscDrawAxis *axis)
22: {
23: PetscDrawAxis ad;
24: PetscObject obj = (PetscObject)draw;
26: PetscBool isnull;
31: PetscObjectTypeCompare(obj,PETSC_DRAW_NULL,&isnull);
32: if (isnull) {
33: PetscDrawOpenNull(PetscObjectComm((PetscObject)obj),(PetscDraw*)axis);
35: (*axis)->win = draw;
36: return(0);
37: }
38: PetscHeaderCreate(ad,_p_PetscDrawAxis,int,PETSC_DRAWAXIS_CLASSID,"PetscDrawAxis","Draw Axis","Draw",PetscObjectComm((PetscObject)obj),PetscDrawAxisDestroy,0);
39: PetscLogObjectParent(draw,ad);
41: ad->xticks = PetscADefTicks;
42: ad->yticks = PetscADefTicks;
43: ad->xlabelstr = PetscADefLabel;
44: ad->ylabelstr = PetscADefLabel;
45: ad->win = draw;
46: ad->ac = PETSC_DRAW_BLACK;
47: ad->tc = PETSC_DRAW_BLACK;
48: ad->cc = PETSC_DRAW_BLACK;
49: ad->xlabel = 0;
50: ad->ylabel = 0;
51: ad->toplabel = 0;
53: *axis = ad;
54: return(0);
55: }
59: /*@
60: PetscDrawAxisDestroy - Frees the space used by an axis structure.
62: Collective over PetscDrawAxis
64: Input Parameters:
65: . axis - the axis context
67: Level: advanced
69: @*/
70: PetscErrorCode PetscDrawAxisDestroy(PetscDrawAxis *axis)
71: {
75: if (!*axis) return(0);
76: if (--((PetscObject)(*axis))->refct > 0) return(0);
78: PetscFree((*axis)->toplabel);
79: PetscFree((*axis)->xlabel);
80: PetscFree((*axis)->ylabel);
81: PetscHeaderDestroy(axis);
82: return(0);
83: }
87: /*@
88: PetscDrawAxisSetColors - Sets the colors to be used for the axis,
89: tickmarks, and text.
91: Not Collective (ignored on all processors except processor 0 of PetscDrawAxis)
93: Input Parameters:
94: + axis - the axis
95: . ac - the color of the axis lines
96: . tc - the color of the tick marks
97: - cc - the color of the text strings
99: Level: advanced
101: @*/
102: PetscErrorCode PetscDrawAxisSetColors(PetscDrawAxis axis,int ac,int tc,int cc)
103: {
105: if (!axis) return(0);
106: axis->ac = ac; axis->tc = tc; axis->cc = cc;
107: return(0);
108: }
112: /*@C
113: PetscDrawAxisSetLabels - Sets the x and y axis labels.
115: Not Collective (ignored on all processors except processor 0 of PetscDrawAxis)
117: Input Parameters:
118: + axis - the axis
119: . top - the label at the top of the image
120: - xlabel,ylabel - the labes for the x and y axis
122: Notes: Must be called before PetscDrawAxisDraw() or PetscDrawLGDraw()
123: There should be no newlines in the arguments
125: Level: advanced
127: @*/
128: PetscErrorCode PetscDrawAxisSetLabels(PetscDrawAxis axis,const char top[],const char xlabel[],const char ylabel[])
129: {
133: if (!axis) return(0);
134: PetscFree(axis->xlabel);
135: PetscFree(axis->ylabel);
136: PetscFree(axis->toplabel);
137: PetscStrallocpy(xlabel,&axis->xlabel);
138: PetscStrallocpy(ylabel,&axis->ylabel);
139: PetscStrallocpy(top,&axis->toplabel);
140: return(0);
141: }
145: /*@
146: PetscDrawAxisSetHoldLimits - Causes an axis to keep the same limits until this is called
147: again
149: Not Collective (ignored on all processors except processor 0 of PetscDrawAxis)
151: Input Parameters:
152: + axis - the axis
153: - hold - PETSC_TRUE - hold current limits, PETSC_FALSE allow limits to be changed
155: Level: advanced
157: Notes:
158: Once this has been called with PETSC_TRUE the limits will not change if you call
159: PetscDrawAxisSetLimits() until you call this with PETSC_FALSE
161: .seealso: PetscDrawAxisSetLimits()
163: @*/
164: PetscErrorCode PetscDrawAxisSetHoldLimits(PetscDrawAxis axis,PetscBool hold)
165: {
167: if (!axis) return(0);
168: axis->hold = hold;
169: return(0);
170: }
174: /*@
175: PetscDrawAxisDraw - PetscDraws an axis.
177: Not Collective (ignored on all processors except processor 0 of PetscDrawAxis)
179: Input Parameter:
180: . axis - Axis structure
182: Level: advanced
184: Note:
185: This draws the actual axis. The limits etc have already been set.
186: By picking special routines for the ticks and labels, special
187: effects may be generated. These routines are part of the Axis
188: structure (axis).
189: @*/
190: PetscErrorCode PetscDrawAxisDraw(PetscDrawAxis axis)
191: {
192: int i,ntick,numx,numy,ac = axis->ac,tc = axis->tc,cc = axis->cc,rank;
193: size_t len;
194: PetscReal tickloc[MAXSEGS],sep,h,w,tw,th,xl,xr,yl,yr;
195: char *p;
196: PetscDraw draw = axis->win;
200: if (!axis) return(0);
201: MPI_Comm_rank(PetscObjectComm((PetscObject)axis),&rank);
202: if (rank) return(0);
204: if (axis->xlow == axis->xhigh) {axis->xlow -= .5; axis->xhigh += .5;}
205: /* if ((axis->yhigh - axis->ylow) <= 1.e-5*PetscMax(PetscAbsReal(axis->yhigh),PetscAbsReal(axis->ylow))) {
206: axis->ylow -= 1.e-5*PetscMax(PetscAbsReal(axis->yhigh),PetscAbsReal(axis->ylow));
207: axis->yhigh += 1.e-5*PetscMax(PetscAbsReal(axis->yhigh),PetscAbsReal(axis->ylow));
208: } */
209: if (axis->ylow == axis->yhigh) {axis->ylow -= .5; axis->yhigh += .5;}
211: xl = axis->xlow; xr = axis->xhigh; yl = axis->ylow; yr = axis->yhigh;
212: PetscDrawSetCoordinates(draw,xl,yl,xr,yr);
213: PetscDrawStringGetSize(draw,&tw,&th);
214: numx = (int)(.15*(xr-xl)/tw); if (numx > 6) numx = 6;if (numx< 2) numx = 2;
215: numy = (int)(.50*(yr-yl)/th); if (numy > 6) numy = 6;if (numy< 2) numy = 2;
216: xl -= 11*tw; xr += 2*tw; yl -= 2.5*th; yr += 2*th;
217: if (axis->xlabel) yl -= 2*th;
218: if (axis->ylabel) xl -= 2*tw;
219: PetscDrawSetCoordinates(draw,xl,yl,xr,yr);
220: PetscDrawStringGetSize(draw,&tw,&th);
222: PetscDrawLine(draw,axis->xlow,axis->ylow,axis->xhigh,axis->ylow,ac);
223: PetscDrawLine(draw,axis->xlow,axis->ylow,axis->xlow,axis->yhigh,ac);
225: if (axis->toplabel) {
226: PetscStrlen(axis->toplabel,&len);
227: w = xl + .5*(xr - xl) - .5*len*tw;
228: h = axis->yhigh;
229: PetscDrawString(draw,w,h,cc,axis->toplabel);
230: }
232: /* PetscDraw the ticks and labels */
233: if (axis->xticks) {
234: (*axis->xticks)(axis->xlow,axis->xhigh,numx,&ntick,tickloc,MAXSEGS);
235: /* PetscDraw in tick marks */
236: for (i=0; i<ntick; i++) {
237: PetscDrawLine(draw,tickloc[i],axis->ylow-.5*th,tickloc[i],axis->ylow+.5*th,tc);
238: }
239: /* label ticks */
240: for (i=0; i<ntick; i++) {
241: if (axis->xlabelstr) {
242: if (i < ntick - 1) sep = tickloc[i+1] - tickloc[i];
243: else if (i > 0) sep = tickloc[i] - tickloc[i-1];
244: else sep = 0.0;
245: (*axis->xlabelstr)(tickloc[i],sep,&p);
246: PetscStrlen(p,&len);
247: w = .5*len*tw;
248: PetscDrawString(draw,tickloc[i]-w,axis->ylow-1.2*th,cc,p);
249: }
250: }
251: }
252: if (axis->xlabel) {
253: PetscStrlen(axis->xlabel,&len);
254: w = xl + .5*(xr - xl) - .5*len*tw;
255: h = axis->ylow - 2.5*th;
256: PetscDrawString(draw,w,h,cc,axis->xlabel);
257: }
258: if (axis->yticks) {
259: (*axis->yticks)(axis->ylow,axis->yhigh,numy,&ntick,tickloc,MAXSEGS);
260: /* PetscDraw in tick marks */
261: for (i=0; i<ntick; i++) {
262: PetscDrawLine(draw,axis->xlow -.5*tw,tickloc[i],axis->xlow+.5*tw,tickloc[i],tc);
263: }
264: /* label ticks */
265: for (i=0; i<ntick; i++) {
266: if (axis->ylabelstr) {
267: if (i < ntick - 1) sep = tickloc[i+1] - tickloc[i];
268: else if (i > 0) sep = tickloc[i] - tickloc[i-1];
269: else sep = 0.0;
270: (*axis->xlabelstr)(tickloc[i],sep,&p);
271: PetscStrlen(p,&len);
272: w = axis->xlow - len * tw - 1.2*tw;
273: PetscDrawString(draw,w,tickloc[i]-.5*th,cc,p);
274: }
275: }
276: }
277: if (axis->ylabel) {
278: PetscStrlen(axis->ylabel,&len);
279: h = yl + .5*(yr - yl) + .5*len*th;
280: w = xl + 1.5*tw;
281: PetscDrawStringVertical(draw,w,h,cc,axis->ylabel);
282: }
283: return(0);
284: }
288: /*
289: Removes all zeros but one from .0000
290: */
291: PetscErrorCode PetscStripe0(char *buf)
292: {
294: size_t n;
295: PetscBool flg;
296: char *str;
299: PetscStrlen(buf,&n);
300: PetscStrendswith(buf,"e00",&flg);
301: if (flg) buf[n-3] = 0;
302: PetscStrstr(buf,"e0",&str);
303: if (str) {
304: buf[n-2] = buf[n-1];
305: buf[n-1] = 0;
306: }
307: PetscStrstr(buf,"e-0",&str);
308: if (str) {
309: buf[n-2] = buf[n-1];
310: buf[n-1] = 0;
311: }
312: return(0);
313: }
317: /*
318: Removes all zeros but one from .0000
319: */
320: PetscErrorCode PetscStripAllZeros(char *buf)
321: {
323: size_t i,n;
326: PetscStrlen(buf,&n);
327: if (buf[0] != '.') return(0);
328: for (i=1; i<n; i++) {
329: if (buf[i] != '0') return(0);
330: }
331: buf[0] = '0';
332: buf[1] = 0;
333: return(0);
334: }
338: /*
339: Removes trailing zeros
340: */
341: PetscErrorCode PetscStripTrailingZeros(char *buf)
342: {
344: char *found;
345: size_t i,n,m = PETSC_MAX_INT;
348: /* if there is an e in string DO NOT strip trailing zeros */
349: PetscStrchr(buf,'e',&found);
350: if (found) return(0);
352: PetscStrlen(buf,&n);
353: /* locate decimal point */
354: for (i=0; i<n; i++) {
355: if (buf[i] == '.') {m = i; break;}
356: }
357: /* if not decimal point then no zeros to remove */
358: if (m == PETSC_MAX_INT) return(0);
359: /* start at right end of string removing 0s */
360: for (i=n-1; i>m; i++) {
361: if (buf[i] != '0') return(0);
362: buf[i] = 0;
363: }
364: return(0);
365: }
369: /*
370: Removes leading 0 from 0.22 or -0.22
371: */
372: PetscErrorCode PetscStripInitialZero(char *buf)
373: {
375: size_t i,n;
378: PetscStrlen(buf,&n);
379: if (buf[0] == '0') {
380: for (i=0; i<n; i++) buf[i] = buf[i+1];
381: } else if (buf[0] == '-' && buf[1] == '0') {
382: for (i=1; i<n; i++) buf[i] = buf[i+1];
383: }
384: return(0);
385: }
389: /*
390: Removes the extraneous zeros in numbers like 1.10000e6
391: */
392: PetscErrorCode PetscStripZeros(char *buf)
393: {
395: size_t i,j,n;
398: PetscStrlen(buf,&n);
399: if (n<5) return(0);
400: for (i=1; i<n-1; i++) {
401: if (buf[i] == 'e' && buf[i-1] == '0') {
402: for (j=i; j<n+1; j++) buf[j-1] = buf[j];
403: PetscStripZeros(buf);
404: return(0);
405: }
406: }
407: return(0);
408: }
412: /*
413: Removes the plus in something like 1.1e+2 or 1.1e+02
414: */
415: PetscErrorCode PetscStripZerosPlus(char *buf)
416: {
418: size_t i,j,n;
421: PetscStrlen(buf,&n);
422: if (n<5) return(0);
423: for (i=1; i<n-2; i++) {
424: if (buf[i] == '+') {
425: if (buf[i+1] == '0') {
426: for (j=i+1; j<n; j++) buf[j-1] = buf[j+1];
427: return(0);
428: } else {
429: for (j=i+1; j<n+1; j++) buf[j-1] = buf[j];
430: return(0);
431: }
432: } else if (buf[i] == '-') {
433: if (buf[i+1] == '0') {
434: for (j=i+1; j<n; j++) buf[j] = buf[j+1];
435: return(0);
436: }
437: }
438: }
439: return(0);
440: }