Actual source code: zoom.c

  1: #include <petscdraw.h>

  3: #if defined(__GNUC__) && !defined(__clang__)
  4:   #pragma GCC diagnostic push
  5:   #pragma GCC diagnostic ignored "-Wclobbered"
  6: #endif
  7: /*@
  8:   PetscDrawZoom - Allows one to provide a function that gets called for zooming in on a drawing using the mouse buttons

 10:   Collective draw

 12:   Input Parameters:
 13: + draw - the window where the graph will be made.
 14: . func - users function that draws the graphic
 15: - ctx  - pointer to any application required data

 17:   Calling sequence of func:
 18: + draw - the `PetscDraw` object to zoom on
 19: - ctx  - the context for the zooming operation

 21:   Level: advanced

 23: .seealso: `PetscDraw`, `PetscDrawCreate()`
 24: @*/
 25: PetscErrorCode PetscDrawZoom(PetscDraw draw, PetscErrorCode (*func)(PetscDraw draw, PetscCtx ctx), PetscCtx ctx)
 26: {
 27:   PetscDrawButton button;
 28:   PetscReal       dpause, xc, yc, scale = 1.0, w, h, xr, xl, yr, yl, xmin, xmax, ymin, ymax;
 29:   PetscBool       isnull;

 31:   PetscFunctionBegin;
 32:   PetscCall(PetscDrawIsNull(draw, &isnull));
 33:   if (isnull) PetscFunctionReturn(PETSC_SUCCESS);

 35:   PetscCall(PetscDrawCheckResizedWindow(draw));
 36:   PetscCall(PetscDrawClear(draw));
 37:   PetscDrawCollectiveBegin(draw);
 38:   PetscCall((*func)(draw, ctx));
 39:   PetscDrawCollectiveEnd(draw);
 40:   PetscCall(PetscDrawFlush(draw));

 42:   PetscCall(PetscDrawGetPause(draw, &dpause));
 43:   if (dpause >= 0) {
 44:     PetscCall(PetscSleep(dpause));
 45:     goto theend;
 46:   }
 47:   if (dpause != -1) goto theend;

 49:   PetscCall(PetscDrawGetMouseButton(draw, &button, &xc, &yc, NULL, NULL));
 50:   PetscCall(PetscDrawGetCoordinates(draw, &xl, &yl, &xr, &yr));
 51:   xmin = xl;
 52:   xmax = xr;
 53:   w    = xr - xl;
 54:   ymin = yl;
 55:   ymax = yr;
 56:   h    = yr - yl;

 58:   while (button != PETSC_BUTTON_NONE && button != PETSC_BUTTON_RIGHT) {
 59:     switch (button) {
 60:     case PETSC_BUTTON_LEFT:
 61:       scale = 0.5;
 62:       break;
 63:     case PETSC_BUTTON_CENTER:
 64:       scale = 2.0;
 65:       break;
 66:     case PETSC_BUTTON_WHEEL_UP:
 67:       scale = 8 / 10.;
 68:       break;
 69:     case PETSC_BUTTON_WHEEL_DOWN:
 70:       scale = 10 / 8.;
 71:       break;
 72:     default:
 73:       scale = 1.0;
 74:     }
 75:     xl = scale * (xl + w - xc) + xc - w * scale;
 76:     xr = scale * (xr - w - xc) + xc + w * scale;
 77:     yl = scale * (yl + h - yc) + yc - h * scale;
 78:     yr = scale * (yr - h - yc) + yc + h * scale;
 79:     w *= scale;
 80:     h *= scale;
 81:     PetscCall(PetscDrawClear(draw));
 82:     PetscCall(PetscDrawSetCoordinates(draw, xl, yl, xr, yr));
 83:     PetscDrawCollectiveBegin(draw);
 84:     PetscCall((*func)(draw, ctx));
 85:     PetscDrawCollectiveEnd(draw);
 86:     PetscCall(PetscDrawFlush(draw));
 87:     PetscCall(PetscDrawGetMouseButton(draw, &button, &xc, &yc, NULL, NULL));
 88:   }
 89:   PetscCall(PetscDrawSetCoordinates(draw, xmin, ymin, xmax, ymax));
 90: theend:
 91:   PetscFunctionReturn(PETSC_SUCCESS);
 92: }
 93: #if defined(__GNUC__) && !defined(__clang__)
 94:   #pragma GCC diagnostic pop
 95: #endif