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

📄 textutilities.java

📁 JCommon is a Java class library that is used by JFreeChart, Pentaho Reporting and a few other projec
💻 JAVA
📖 第 1 页 / 共 3 页
字号:
        drawRotatedString(text, g2, x + textAdj[0], y + textAdj[1],
                angle, x + textAdj[0] + rotateAdj[0],
                y + textAdj[1] + rotateAdj[1]);

    }

    /**
     * Returns a shape that represents the bounds of the string after the
     * specified rotation has been applied.
     *
     * @param text  the text (<code>null</code> permitted).
     * @param g2  the graphics device.
     * @param x  the x coordinate for the anchor point.
     * @param y  the y coordinate for the anchor point.
     * @param textAnchor  the text anchor.
     * @param angle  the angle.
     * @param rotationAnchor  the rotation anchor.
     *
     * @return The bounds (possibly <code>null</code>).
     */
    public static Shape calculateRotatedStringBounds(final String text,
            final Graphics2D g2, final float x, final float y,
            final TextAnchor textAnchor, final double angle,
            final TextAnchor rotationAnchor) {

        if (text == null || text.equals("")) {
            return null;
        }
        final float[] textAdj = deriveTextBoundsAnchorOffsets(g2, text,
                textAnchor);
        if (logger.isDebugEnabled()) {
            logger.debug("TextBoundsAnchorOffsets = " + textAdj[0] + ", "
                    + textAdj[1]);
        }
        final float[] rotateAdj = deriveRotationAnchorOffsets(g2, text,
                rotationAnchor);
        if (logger.isDebugEnabled()) {
            logger.debug("RotationAnchorOffsets = " + rotateAdj[0] + ", "
                    + rotateAdj[1]);
        }
        final Shape result = calculateRotatedStringBounds(text, g2,
                x + textAdj[0], y + textAdj[1], angle,
                x + textAdj[0] + rotateAdj[0], y + textAdj[1] + rotateAdj[1]);
        return result;

    }

    /**
     * A utility method that calculates the anchor offsets for a string.
     * Normally, the (x, y) coordinate for drawing text is a point on the
     * baseline at the left of the text string.  If you add these offsets to
     * (x, y) and draw the string, then the anchor point should coincide with
     * the (x, y) point.
     *
     * @param g2  the graphics device (not <code>null</code>).
     * @param text  the text.
     * @param anchor  the anchor point.
     *
     * @return  The offsets.
     */
    private static float[] deriveTextBoundsAnchorOffsets(final Graphics2D g2,
            final String text, final TextAnchor anchor) {

        final float[] result = new float[2];
        final FontRenderContext frc = g2.getFontRenderContext();
        final Font f = g2.getFont();
        final FontMetrics fm = g2.getFontMetrics(f);
        final Rectangle2D bounds = TextUtilities.getTextBounds(text, g2, fm);
        final LineMetrics metrics = f.getLineMetrics(text, frc);
        final float ascent = metrics.getAscent();
        final float halfAscent = ascent / 2.0f;
        final float descent = metrics.getDescent();
        final float leading = metrics.getLeading();
        float xAdj = 0.0f;
        float yAdj = 0.0f;

        if (anchor == TextAnchor.TOP_CENTER
                || anchor == TextAnchor.CENTER
                || anchor == TextAnchor.BOTTOM_CENTER
                || anchor == TextAnchor.BASELINE_CENTER
                || anchor == TextAnchor.HALF_ASCENT_CENTER) {

            xAdj = (float) -bounds.getWidth() / 2.0f;

        }
        else if (anchor == TextAnchor.TOP_RIGHT
                || anchor == TextAnchor.CENTER_RIGHT
                || anchor == TextAnchor.BOTTOM_RIGHT
                || anchor == TextAnchor.BASELINE_RIGHT
                || anchor == TextAnchor.HALF_ASCENT_RIGHT) {

            xAdj = (float) -bounds.getWidth();

        }

        if (anchor == TextAnchor.TOP_LEFT
                || anchor == TextAnchor.TOP_CENTER
                || anchor == TextAnchor.TOP_RIGHT) {

            yAdj = -descent - leading + (float) bounds.getHeight();

        }
        else if (anchor == TextAnchor.HALF_ASCENT_LEFT
                || anchor == TextAnchor.HALF_ASCENT_CENTER
                || anchor == TextAnchor.HALF_ASCENT_RIGHT) {

            yAdj = halfAscent;

        }
        else if (anchor == TextAnchor.CENTER_LEFT
                || anchor == TextAnchor.CENTER
                || anchor == TextAnchor.CENTER_RIGHT) {

            yAdj = -descent - leading + (float) (bounds.getHeight() / 2.0);

        }
        else if (anchor == TextAnchor.BASELINE_LEFT
                || anchor == TextAnchor.BASELINE_CENTER
                || anchor == TextAnchor.BASELINE_RIGHT) {

            yAdj = 0.0f;

        }
        else if (anchor == TextAnchor.BOTTOM_LEFT
                || anchor == TextAnchor.BOTTOM_CENTER
                || anchor == TextAnchor.BOTTOM_RIGHT) {

            yAdj = -metrics.getDescent() - metrics.getLeading();

        }
        result[0] = xAdj;
        result[1] = yAdj;
        return result;

    }

    /**
     * A utility method that calculates the rotation anchor offsets for a
     * string.  These offsets are relative to the text starting coordinate
     * (BASELINE_LEFT).
     *
     * @param g2  the graphics device.
     * @param text  the text.
     * @param anchor  the anchor point.
     *
     * @return  The offsets.
     */
    private static float[] deriveRotationAnchorOffsets(final Graphics2D g2,
            final String text, final TextAnchor anchor) {

        final float[] result = new float[2];
        final FontRenderContext frc = g2.getFontRenderContext();
        final LineMetrics metrics = g2.getFont().getLineMetrics(text, frc);
        final FontMetrics fm = g2.getFontMetrics();
        final Rectangle2D bounds = TextUtilities.getTextBounds(text, g2, fm);
        final float ascent = metrics.getAscent();
        final float halfAscent = ascent / 2.0f;
        final float descent = metrics.getDescent();
        final float leading = metrics.getLeading();
        float xAdj = 0.0f;
        float yAdj = 0.0f;

        if (anchor == TextAnchor.TOP_LEFT
                || anchor == TextAnchor.CENTER_LEFT
                || anchor == TextAnchor.BOTTOM_LEFT
                || anchor == TextAnchor.BASELINE_LEFT
                || anchor == TextAnchor.HALF_ASCENT_LEFT) {

            xAdj = 0.0f;

        }
        else if (anchor == TextAnchor.TOP_CENTER
                || anchor == TextAnchor.CENTER
                || anchor == TextAnchor.BOTTOM_CENTER
                || anchor == TextAnchor.BASELINE_CENTER
                || anchor == TextAnchor.HALF_ASCENT_CENTER) {

            xAdj = (float) bounds.getWidth() / 2.0f;

        }
        else if (anchor == TextAnchor.TOP_RIGHT
                || anchor == TextAnchor.CENTER_RIGHT
                || anchor == TextAnchor.BOTTOM_RIGHT
                || anchor == TextAnchor.BASELINE_RIGHT
                || anchor == TextAnchor.HALF_ASCENT_RIGHT) {

            xAdj = (float) bounds.getWidth();

        }

        if (anchor == TextAnchor.TOP_LEFT
                || anchor == TextAnchor.TOP_CENTER
                || anchor == TextAnchor.TOP_RIGHT) {

            yAdj = descent + leading - (float) bounds.getHeight();

        }
        else if (anchor == TextAnchor.CENTER_LEFT
                || anchor == TextAnchor.CENTER
                || anchor == TextAnchor.CENTER_RIGHT) {

            yAdj = descent + leading - (float) (bounds.getHeight() / 2.0);

        }
        else if (anchor == TextAnchor.HALF_ASCENT_LEFT
                || anchor == TextAnchor.HALF_ASCENT_CENTER
                || anchor == TextAnchor.HALF_ASCENT_RIGHT) {

            yAdj = -halfAscent;

        }
        else if (anchor == TextAnchor.BASELINE_LEFT
                || anchor == TextAnchor.BASELINE_CENTER
                || anchor == TextAnchor.BASELINE_RIGHT) {

            yAdj = 0.0f;

        }
        else if (anchor == TextAnchor.BOTTOM_LEFT
                || anchor == TextAnchor.BOTTOM_CENTER
                || anchor == TextAnchor.BOTTOM_RIGHT) {

            yAdj = metrics.getDescent() + metrics.getLeading();

        }
        result[0] = xAdj;
        result[1] = yAdj;
        return result;

    }

    /**
     * Returns a shape that represents the bounds of the string after the
     * specified rotation has been applied.
     *
     * @param text  the text (<code>null</code> permitted).
     * @param g2  the graphics device.
     * @param textX  the x coordinate for the text.
     * @param textY  the y coordinate for the text.
     * @param angle  the angle.
     * @param rotateX  the x coordinate for the rotation point.
     * @param rotateY  the y coordinate for the rotation point.
     *
     * @return The bounds (<code>null</code> if <code>text</code> is
     *         </code>null</code> or has zero length).
     */
    public static Shape calculateRotatedStringBounds(final String text,
            final Graphics2D g2, final float textX, final float textY,
            final double angle, final float rotateX, final float rotateY) {

        if ((text == null) || (text.equals(""))) {
            return null;
        }
        final FontMetrics fm = g2.getFontMetrics();
        final Rectangle2D bounds = TextUtilities.getTextBounds(text, g2, fm);
        final AffineTransform translate = AffineTransform.getTranslateInstance(
                textX, textY);
        final Shape translatedBounds = translate.createTransformedShape(bounds);
        final AffineTransform rotate = AffineTransform.getRotateInstance(
                angle, rotateX, rotateY);
        final Shape result = rotate.createTransformedShape(translatedBounds);
        return result;

    }

    /**
     * Returns the flag that controls whether the FontMetrics.getStringBounds()
     * method is used or not.  If you are having trouble with label alignment
     * or positioning, try changing the value of this flag.
     *
     * @return A boolean.
     */
    public static boolean getUseFontMetricsGetStringBounds() {
        return useFontMetricsGetStringBounds;
    }

    /**
     * Sets the flag that controls whether the FontMetrics.getStringBounds()
     * method is used or not.  If you are having trouble with label alignment
     * or positioning, try changing the value of this flag.
     *
     * @param use  the flag.
     */
    public static void setUseFontMetricsGetStringBounds(final boolean use) {
        useFontMetricsGetStringBounds = use;
    }

    /**
     * Returns the flag that controls whether or not a workaround is used for
     * drawing rotated strings.
     *
     * @return A boolean.
     */
    public static boolean isUseDrawRotatedStringWorkaround() {
        return useDrawRotatedStringWorkaround;
    }
}

⌨️ 快捷键说明

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