⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 gannotator.java

📁 use Java code to draw on pad canvas
💻 JAVA
📖 第 1 页 / 共 2 页
字号:
package no.geosoft.cc.graphics;import java.util.Collection;import java.util.Iterator;import no.geosoft.cc.geometry.Geometry;import no.geosoft.cc.geometry.Region;import no.geosoft.cc.geometry.Rect;/** * Layout manager for positionals. Positionals are object attached * to graphic elements by means of rendering hints. *  * @author <a href="mailto:jacob.dreyer@geosoft.no">Jacob Dreyer</a> */   class GAnnotator{  private static final int     MAX_ATTEMTS = 300;  private static final double  DLENGTH     = 8.0;      private final GScene  scene_;     private final Region  region_;  // Annotation region  // Precomputed viewport numbers for speed  private int     vx0_, vy0_;  private int     vx1_, vy1_;    private int     vx2_, vy2_;  private int     vx3_, vy3_;    // Working variable during annotation  private double  distance_;    /**   * Create annotator for the specified scene. The annotator use the   * scene viewport as its canvas, and position all positional elements   * of the scene inside this region.   *    * @param scene  Scene of this annotator.   */  GAnnotator (GScene scene)  {    region_  = new Region();    scene_ = scene;  }    /**   * Reset this annotator. The annotator must be reset when the scene   * viewport is changed.   */  void reset()  {    region_.set (scene_.getRegion());    // Precompute some viewport numbers    GViewport viewport = scene_.getViewport();    int p0[] = viewport.getP0();  // x,y    int p1[] = viewport.getP1();  // x,y    int p2[] = viewport.getP2();  // x,y        vx0_ = p0[0];    vy0_ = p0[1];        vx1_ = p1[0];    vy1_ = p1[1];        vx2_ = p2[0];    vy2_ = p2[1];        vx3_ = vx2_ + vx1_ - vx0_;    vy3_ = vy1_ + vy2_ - vy0_;       }  /**   * Compute the x and y position of the specified positional elements   * and set isVisible flag in case they are outside the screen.   * After this computation is done on all nodes, the positionals can be   * rendered directly by the GCanvas object.   *    * @param positionals  Elements to position (of GPositional).   */  void computePositions (Collection positionals)  {    // Return here if nothing to position    if (positionals == null) return;    int objectNo = 0;    for (Iterator i = positionals.iterator(); i.hasNext(); ) {      GPositional positional = (GPositional) i.next();      GSegment segment = positional.getSegment();      int positionHint = positional.getPositionHint();            // Save a copy of the old rectangle      Rect oldRectangle = new Rect (positional.getRectangle());      boolean wasVisible = positional.isVisible();            if (segment.isVisible()) {        int x[] = segment.getX();        int y[] = segment.getY();        int x0  = segment.getCenterX();        int y0  = segment.getCenterY();                // Compute positional size        positional.computeSize();        if (positional.getRectangle().isEmpty()) {          positional.setVisible (false);          continue;        }                // Find the preferred annotation according to line position hints        int pointNo = findPreferredPosition (positional, x, y, x0, y0,                                             objectNo);        // If the current point is outside the viewport move it inside         if ((positionHint & GPosition.DYNAMIC) != 0 &&            (positionHint & GPosition.MIDDLE) == 0) {          positional.setVisible (true);          distance_ = 0.0;          if (!scene_.getRegion().isInside (positional.getRectangle().x,                                            positional.getRectangle().y))            pointNo = moveInsideWindow (positional, x, y, pointNo);        }        else {          positional.setVisible (scene_.getRegion().                                 isInside (positional.getRectangle().x,                                           positional.getRectangle().y));        }                if (positional.isVisible()) {                    // Tune the positional according to point position hint          adjustPosition (positional);          // For a static positional we're now done          if ((positionHint & GPosition.STATIC) != 0 |              (positionHint & GPosition.MIDDLE) != 0)            positional.setVisible (region_.isIntersecting (positional.                                                           getRectangle()));          else { // GPosition.DYNAMIC and don't allow overlapping            if (!positional.isAllowingOverlaps() &&                !region_.isInside (positional.getRectangle()))              findNonOverlappingPosition (positional, x, y, pointNo);          }        }      }      // If positional was moved update damage      if (!oldRectangle.equals (positional.getRectangle())) {        if (wasVisible)          scene_.getWindow().updateDamageArea (oldRectangle);        if (positional.isVisible())          scene_.getWindow().updateDamageArea (positional.getRectangle());        if (wasVisible || positional.isVisible())          segment.getOwner().flagRegionValid (false);      }      // If a valid position was found update the annotation region      if (positional.isVisible() &&          (positional.getPositionHint() & GPosition.STATIC) == 0 &&          !positional.isAllowingOverlaps())        region_.subtract (positional.getRectangle());      if (!positional.isLinePositional()) objectNo++;    }  }    /**   * Find the preferred position of a positional element. This is the   * position as dictaed by its rendering hint and before any adjustments   * are done.   *    * @param positional  Positional element to position.   * @param x           X values of polyline to position according to.   * @param y           Y values of polyline to position according to.      * @param x0          X coordinate of center of gravity of polyline   *                    (used with rendering hint MIDDLE).   * @param y0          Y coordinate of center of gravity of polyline   *                    (used with rendering hint MIDDLE).   * @param pointNo     Index number of this positional on this polyline   *                    (used when no line rendering hints are given).   * @return            Index in x,y of point to attach this positional to.   */  private int findPreferredPosition (GPositional positional,                                     int x[], int y[], int x0, int y0,                                     int pointNo)  {    int positionHint = positional.getPositionHint();    int nPoints  = x.length;    if (positional.isLinePositional()) {            // Find the point on the segment that the positional should attach to      if ((positionHint & GPosition.LAST) != 0) {        pointNo = nPoints - 1;      }      else if ((positionHint & GPosition.MIDDLE) != 0) {        positional.getRectangle().x = x0;        positional.getRectangle().y = y0;        return -1;      }      else if ((positionHint & GPosition.TOP) != 0) {        int yMin = y[0];        for (int i = 0; i < nPoints; i++) {          if (y[i] < yMin) {            yMin = y[i];            pointNo = i;          }        }      }      else if ((positionHint & GPosition.BOTTOM) != 0) {        int yMax = y[0];        for (int i = 0; i < nPoints; i++) {          if (y[i] > yMax) {            yMax = y[i];            pointNo = i;          }        }      }      else if ((positionHint & GPosition.LEFT) != 0) {        int xMin = x[0];        for (int i = 0; i < nPoints; i++) {          if (x[i] < xMin) {            xMin = x[i];            pointNo = i;          }        }      }      else if ((positionHint & GPosition.RIGHT) != 0) {        int xMax = x[0];        for (int i = 0; i < nPoints; i++) {          if (x[i] > xMax) {            xMax = x[i];            pointNo = i;          }        }      }    }        positional.getRectangle().x = x[pointNo];    positional.getRectangle().y = y[pointNo];    return pointNo;  }    /**   * Adjsut the position of the specified positional according to   * point position hint.   *    * @param positional  Positionla to adjust.   */  private void adjustPosition (GPositional positional)  {    int positionHint = positional.getPositionHint();    int x            = positional.getRectangle().x;    int y            = positional.getRectangle().y;    int width        = positional.getRectangle().width;    int height       = positional.getRectangle().height;    int halfWidth  = (int) Math.ceil ((double) width  / 2.0);    int halfHeight = (int) Math.ceil ((double) height / 2.0);                            if ((positionHint & GPosition.NORTHWEST) != 0) {      x -= width  + positional.getMargin();      y -= height + positional.getMargin();    }    else if ((positionHint & GPosition.NORTHEAST) != 0) {      x += positional.getMargin();      y -= height + positional.getMargin();    }    else if ((positionHint & GPosition.SOUTHWEST) != 0) {      x -= width  + positional.getMargin();      y += positional.getMargin();    }    else if ((positionHint & GPosition.SOUTHEAST) != 0) {      x += positional.getMargin();      y += positional.getMargin();    }    else if ((positionHint & GPosition.NORTH) != 0) {      x -= halfWidth;      y -= height + positional.getMargin();    }    else if ((positionHint & GPosition.WEST) != 0) {      x -= width  + positional.getMargin();      y -= halfHeight;    }    else if ((positionHint & GPosition.EAST) != 0) {      x += positional.getMargin();      y -= halfHeight;    }    else if ((positionHint & GPosition.SOUTH) != 0) {      x -= halfWidth;      y += positional.getMargin();    }    else { // GPosition.CENTER      x -= halfWidth;      y -= halfHeight;    }    positional.getRectangle().x = x;    positional.getRectangle().y = y;  }    /**   * Adjust position of the specified positional so that it doesn't overlap

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -