📄 mxgraphoutline.java
字号:
tripleBufferGraphics.dispose(); tripleBufferGraphics = null; } } /** * Clears and repaints the triple buffer at the given rectangle or repaints * the complete buffer if no rectangle is specified. * * @param clip */ public void repaintTripleBuffer(Rectangle clip) { if (tripleBuffered && tripleBufferGraphics != null) { if (clip == null) { clip = new Rectangle(tripleBuffer.getWidth(), tripleBuffer .getHeight()); } // Clears and repaints the dirty rectangle using the // graphics canvas of the graph component as a renderer mxUtils.clearRect(tripleBufferGraphics, clip, null); tripleBufferGraphics.setClip(clip); paintGraph(tripleBufferGraphics); tripleBufferGraphics.setClip(null); repaintBuffer = false; repaintClip = null; } } /** * */ public void updateFinder(boolean repaint) { Rectangle rect = graphComponent.getViewport().getViewRect(); int x = (int) Math.round(rect.x * scale); int y = (int) Math.round(rect.y * scale); int w = (int) Math.round((rect.x + rect.width) * scale) - x; int h = (int) Math.round((rect.y + rect.height) * scale) - y; updateFinderBounds(new Rectangle(x + translate.x, y + translate.y, w + 1, h + 1), repaint); } /** * */ public void updateFinderBounds(Rectangle bounds, boolean repaint) { if (bounds != null && !bounds.equals(finderBounds)) { Rectangle old = new Rectangle(finderBounds); finderBounds = bounds; // LATER: Fix repaint region to be smaller if (repaint) { old = old.union(finderBounds); old.grow(3, 3); repaint(old); } } } /** * */ public void paintComponent(Graphics g) { super.paintComponent(g); paintBackground(g); if (graphComponent != null) { // Creates or destroys the triple buffer as needed if (tripleBuffered) { checkTripleBuffer(); } else if (tripleBuffer != null) { destroyTripleBuffer(); } // Updates the dirty region from the buffered graph image if (tripleBuffer != null) { if (repaintBuffer) { repaintTripleBuffer(null); } else if (repaintClip != null) { repaintClip.grow(1 / scale); repaintClip.setX(repaintClip.getX() * scale + translate.x); repaintClip.setY(repaintClip.getY() * scale + translate.y); repaintClip.setWidth(repaintClip.getWidth() * scale); repaintClip.setHeight(repaintClip.getHeight() * scale); repaintTripleBuffer(repaintClip.getRectangle()); } mxUtils.drawImageClip(g, tripleBuffer, this); } // Paints the graph directly onto the graphics else { paintGraph(g); } paintForeground(g); } } /** * Paints the background. */ protected void paintBackground(Graphics g) { if (graphComponent != null) { Graphics2D g2 = (Graphics2D) g; AffineTransform tx = g2.getTransform(); try { // Draws the background of the outline if a graph exists g.setColor(graphComponent.getPageBackgroundColor()); mxUtils.fillClippedRect(g, 0, 0, getWidth(), getHeight()); g2.translate(translate.x, translate.y); g2.scale(scale, scale); // Draws the scaled page background if (!graphComponent.isPageVisible()) { g.setColor(graphComponent.getBackground()); Dimension size = graphComponent.getGraphControl().getSize(); // Paints the background of the drawing surface mxUtils.fillClippedRect(g, 0, 0, size.width, size.height); g.setColor(g.getColor().darker().darker()); g.drawRect(0, 0, size.width, size.height); } else { // Paints the page background using the graphics scaling graphComponent.paintBackgroundPage(g); } } finally { g2.setTransform(tx); } } else { // Draws the background of the outline if no graph exists g.setColor(getBackground()); mxUtils.fillClippedRect(g, 0, 0, getWidth(), getHeight()); } } /** * Paints the graph outline. */ public void paintGraph(Graphics g) { if (graphComponent != null) { Graphics2D g2 = (Graphics2D) g; AffineTransform tx = g2.getTransform(); try { g2.translate(translate.x, translate.y); g2.scale(scale, scale); // Draws the scaled graph graphComponent.paintGraph(g2, drawLabels); } finally { g2.setTransform(tx); } } } /** * Paints the foreground. Foreground is dynamic and should never be made * part of the triple buffer. It is painted on top of the buffer. */ protected void paintForeground(Graphics g) { if (graphComponent != null) { Graphics2D g2 = (Graphics2D) g; Stroke stroke = g2.getStroke(); g.setColor(Color.BLUE); g2.setStroke(new BasicStroke(3)); g.drawRect(finderBounds.x, finderBounds.y, finderBounds.width, finderBounds.height); g2.setStroke(stroke); g.setColor(DEFAULT_ZOOMHANDLE_FILL); g.fillRect(finderBounds.x + finderBounds.width - 6, finderBounds.y + finderBounds.height - 6, 8, 8); g.setColor(Color.BLACK); g.drawRect(finderBounds.x + finderBounds.width - 6, finderBounds.y + finderBounds.height - 6, 8, 8); } } /** * Returns true if the scale or translate has changed. */ public boolean updateScaleAndTranslate() { double newScale = 1; int dx = 0; int dy = 0; if (this.graphComponent != null) { Dimension graphSize = graphComponent.getGraphControl().getSize(); Dimension outlineSize = getSize(); int gw = (int) graphSize.getWidth(); int gh = (int) graphSize.getHeight(); if (gw > 0 && gh > 0) { boolean magnifyPage = graphComponent.isPageVisible() && isFitPage() && graphComponent.getHorizontalScrollBar().isVisible() && graphComponent.getVerticalScrollBar().isVisible(); double graphScale = graphComponent.getGraph().getView() .getScale(); mxPoint trans = graphComponent.getGraph().getView() .getTranslate(); int w = (int) outlineSize.getWidth() - 2 * outlineBorder; int h = (int) outlineSize.getHeight() - 2 * outlineBorder; if (magnifyPage) { gw -= 2 * Math.round(trans.getX() * graphScale); gh -= 2 * Math.round(trans.getY() * graphScale); } newScale = Math.min((double) w / gw, (double) h / gh); dx += (int) Math .round((outlineSize.getWidth() - gw * newScale) / 2); dy += (int) Math .round((outlineSize.getHeight() - gh * newScale) / 2); if (magnifyPage) { dx -= Math.round(trans.getX() * newScale * graphScale); dy -= Math.round(trans.getY() * newScale * graphScale); } } } if (newScale != scale || translate.x != dx || translate.y != dy) { scale = newScale; translate.setLocation(dx, dy); return true; } else { return false; } } /** * */ public class MouseTracker implements MouseListener, MouseMotionListener { /** * */ protected Point start = null; /* * (non-Javadoc) * @see java.awt.event.MouseListener#mousePressed(java.awt.event.MouseEvent) */ public void mousePressed(MouseEvent e) { zoomGesture = hitZoomHandle(e.getX(), e.getY()); if (graphComponent != null && !e.isConsumed() && !e.isPopupTrigger() && (finderBounds.contains(e.getPoint()) || zoomGesture)) { start = e.getPoint(); } } /* * (non-Javadoc) * @see java.awt.event.MouseMotionListener#mouseDragged(java.awt.event.MouseEvent) */ public void mouseDragged(MouseEvent e) { if (isEnabled() && start != null) { if (zoomGesture) { Rectangle bounds = graphComponent.getViewport() .getViewRect(); double viewRatio = bounds.getWidth() / bounds.getHeight(); bounds = new Rectangle(finderBounds); bounds.width = (int) Math .max(0, (e.getX() - bounds.getX())); bounds.height = (int) Math.max(0, (bounds.getWidth() / viewRatio)); updateFinderBounds(bounds, true); } else { // TODO: To enable constrained moving, that is, moving // into only x- or y-direction when shift is pressed, // we need the location of the first mouse event, since // the movement can not be constrained for incremental // steps as used below. int dx = (int) ((e.getX() - start.getX()) / scale); int dy = (int) ((e.getY() - start.getY()) / scale); // Keeps current location as start for delta movement // of the scrollbars start = e.getPoint(); graphComponent.getHorizontalScrollBar().setValue( graphComponent.getHorizontalScrollBar().getValue() + dx); graphComponent.getVerticalScrollBar().setValue( graphComponent.getVerticalScrollBar().getValue() + dy); } } } /* * (non-Javadoc) * @see java.awt.event.MouseListener#mouseReleased(java.awt.event.MouseEvent) */ public void mouseReleased(MouseEvent e) { if (start != null) { if (zoomGesture) { double dx = e.getX() - start.getX(); double w = finderBounds.getWidth(); final JScrollBar hs = graphComponent .getHorizontalScrollBar(); final double sx; if (hs != null) { sx = (double) hs.getValue() / hs.getMaximum(); } else { sx = 0; } final JScrollBar vs = graphComponent.getVerticalScrollBar(); final double sy; if (vs != null) { sy = (double) vs.getValue() / vs.getMaximum(); } else { sy = 0; } mxGraphView view = graphComponent.getGraph().getView(); double scale = view.getScale(); double newScale = scale - (dx * scale) / w; double factor = newScale / scale; view.setScale(newScale); if (hs != null) { hs.setValue((int) (sx * hs.getMaximum() * factor)); } if (vs != null) { vs.setValue((int) (sy * vs.getMaximum() * factor)); } } zoomGesture = false; start = null; } } /** * */ public boolean hitZoomHandle(int x, int y) { return new Rectangle(finderBounds.x + finderBounds.width - 6, finderBounds.y + finderBounds.height - 6, 8, 8).contains(x, y); } /* * (non-Javadoc) * @see java.awt.event.MouseMotionListener#mouseMoved(java.awt.event.MouseEvent) */ public void mouseMoved(MouseEvent e) { if (hitZoomHandle(e.getX(), e.getY())) { setCursor(new Cursor(Cursor.HAND_CURSOR)); } else if (finderBounds.contains(e.getPoint())) { setCursor(new Cursor(Cursor.MOVE_CURSOR)); } else { setCursor(new Cursor(Cursor.DEFAULT_CURSOR)); } } /* * (non-Javadoc) * @see java.awt.event.MouseListener#mouseClicked(java.awt.event.MouseEvent) */ public void mouseClicked(MouseEvent e) { // ignore } /* * (non-Javadoc) * @see java.awt.event.MouseListener#mouseEntered(java.awt.event.MouseEvent) */ public void mouseEntered(MouseEvent e) { // ignore } /* * (non-Javadoc) * @see java.awt.event.MouseListener#mouseExited(java.awt.event.MouseEvent) */ public void mouseExited(MouseEvent e) { // ignore } }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -