net.sf.jasperreports.engine.fill

## Class TextMeasurer

- java.lang.Object
- - net.sf.jasperreports.engine.fill.TextMeasurer

- All Implemented Interfaces:
    JRTextMeasurer
  Direct Known Subclasses:
    JdkGlyphFixTextMeasurer

      public class TextMeasurer
      extends java.lang.Object
      implements JRTextMeasurer

  Default text measurer implementation.

  ### Text Measuring

  When a the contents of a text element do not fit into the area given by the element width and height, the engine will either truncate the text contents or, in the case of a text field that is allowed to stretch, increase the height of the element to accommodate the contents. To do so, the JasperReports engine needs to measure the text and calculate how much of it fits in the element area, or how much the element needs to stretch in order to fit the entire text.

  JasperReports does this, by default, by using standard Java AWT classes to layout and measure the text with its style information given by the text font and by other style attributes. This ensures that the result of the text layout calculation is exact according to the JasperReports principle of pixel perfectness.

  However, this comes at a price - the AWT text layout calls contribute to the overall report fill performance. For this reason and possibly others, it might be desired in some cases to implement a different text measuring mechanism. JasperReports allows users to employ custom text measurer implementations by setting a value for the `net.sf.jasperreports.text.measurer.factory` property. The property can be set globally (in `jasperreports.properties` or via the `JRPropertiesUtil.setProperty(String, String)` method), at report level or at element level (as an element property). The property value should be either the name of a class that implements the `JRTextMeasurerFactory` interface, or an alias defined for such a text measurer factory class. To define an alias, one needs to define a property having `net.sf.jasperreports.text.measurer.factory.<alias>` as key and the factory class name as value. Take the following examples of text measurer factory properties:
  - in jasperreports.properties set a custom default text measurer factory:
    `net.sf.jasperreports.text.measurer.factory=com.jasperreports.MyTextMeasurerFactory`
  - define an alias for a different text measurer factory:
    `net.sf.jasperreports.text.measurer.factory.fast=com.jasperreports.MyFastTextMeasurerFactory`
  - in a JRXML, use the fast text measurer for a static text:

       <staticText>
         <reportElement ...>
           <property name="net.sf.jasperreports.text.measurer.factory" value="fast"/>
         </reportElement>
         <text>...</text>
       </staticText>

  The default text measurer factory used by JasperReports is `TextMeasurerFactory`; the factory is also registered under an alias named `default`.

  ### Text Truncation

  The built-in text measurer supports a series of text truncation customizations. As a reminder, text truncation occurs when a the contents of a static text element or of a text field that is not set as stretchable do not fit the area reserved for the element in the report template. Note that text truncation only refers to the truncation of the last line of a text element, and not to the word wrapping of a text element that spans across multiple lines.

  The default behavior is to use the standard AWT line break logic (as returned by the `java.text.BreakIterator.getLineInstance()` method) to determine where to truncate the text. This means that the last line of text will be truncated after the last word that fits on the line, or after the last character when the first word on the line does not entirely fit.

  This behavior can be changed by forcing the text to always get truncated at the last character that fits the element area, and by appending one or more characters to the truncated text to notify a report reader that the text has been truncated. To force the text to be wrapped at the last character, the `net.sf.jasperreports.text.truncate.at.char` property needs to be set to true globally, at report level or at text element level. The levels at which the property can be set are listed in a decreasing order of precedence, therefore an element level property overrides the report level property, which in its turn overrides the global property. The property can also be set to false at report or element level to override the true value of the property set at a higher level.

  To append a suffix to the truncated text, one needs to set the desired suffix as the value of the `net.sf.jasperreports.text.truncate.suffix` property globally, at report level or at element level. For instance, to use a Unicode horizontal ellipsis character (code point U+2026) as text truncation suffix, one would set the property globally or at report level as following:
  - globally in `jasperreports.properties`:
    `net.sf.jasperreports.text.truncate.suffix=\u2026`
  - at report level:

       <jasperReport ...>
         <property name="net.sf.jasperreports.text.truncate.suffix" value="&#x2026;"/>
         ...
       </jasperReport>

  Note that in the JRXML the ellipsis character was introduced via an XML numerical character entity. If the JRXML file uses a Unicode XML encoding, the Unicode character can also be directly written in the JRXML.

  When using a truncation suffix, the truncate at character property is taken into consideration in order to determine where to append the truncation suffix. If the truncation at character property is set to false, the suffix is appended after the last word that fits; if the property is set to true, the suffix is appended after the last text character that fits.

  When used for a text element that produces styled text, the truncation suffix is placed outside the styled text, that is, the truncation suffix will be displayed using the style defined at element level.

  Text truncation is desirable when producing reports for that are displayed on a screen or printed on paper - in such scenarios the layout of the report is important. On the other hand, some JasperReports exporters, such as the Excel or CSV ones, produce output which in many cases is intended as data-centric. In such cases, it could be useful not to truncate any text generated by the report, even if some texts would not fit when rendered on a layout-sensitive media.

  To inhibit the unconditional truncation of report texts, one would need to set the `net.sf.jasperreports.print.keep.full.text` property to true globally, at report level or at text element level. When the property is set to true, the text is not truncated at fill time and the generated report preserves the full text as produced by the text element.

  Visual report exporters (such as the exporters used for PDF, HTML, RTF, printing or the Java report viewer) would still truncate the rendered text, but the Excel and CSV data-centric exporters would use the full text. Note that preserving the full text does not affect the size of the text element, therefore the Excel exporter would display the full text inside a cell that has the size of the truncated text.
  Version:
    $Id: TextMeasurer.java 7076 2014-05-06 10:10:35Z shertage $
  Author:
    Teodor Danciu (teodord@users.sourceforge.net)
  See Also:
    `JRTextElement.PROPERTY_PRINT_KEEP_FULL_TEXT`, `JRTextElement.PROPERTY_TRUNCATE_AT_CHAR`, `JRTextElement.PROPERTY_TRUNCATE_SUFFIX`, `TextMeasurerFactory`, `JRTextMeasurerUtil.PROPERTY_TEXT_MEASURER_FACTORY`

- - ### Nested Class Summary

    Nested Classes
    Modifier and Type | Class and Description
    --- | ---
    `protected static class` | `TextMeasurer.TextMeasuredState`

  - ### Field Summary

    Fields
    Modifier and Type | Field and Description
    --- | ---
    `protected JasperReportsContext` | `jasperReportsContext`
    `protected int` | `leftPadding`
    `protected int` | `maxHeight`
    `protected TextMeasurer.TextMeasuredState` | `measuredState`
    `protected TextMeasurer.TextMeasuredState` | `prevMeasuredState`
    `static java.lang.String` | `PROPERTY_MEASURE_SIMPLE_TEXTS`
    `protected int` | `rightPadding`
    `protected JRCommonText` | `textElement`
    `protected int` | `width`

  - ### Constructor Summary

    Constructors
    Constructor and Description
    `TextMeasurer(JasperReportsContext jasperReportsContext, JRCommonText textElement)`
    `TextMeasurer(JRCommonText textElement)` Deprecated. Replaced by `TextMeasurer(JasperReportsContext, JRCommonText)`.

  - ### Method Summary

    Methods
    Modifier and Type | Method and Description
    --- | ---
    `protected void` | `appendTruncateSuffix(TextLineWrapper lineWrapper)`
    `java.awt.font.FontRenderContext` | `getFontRenderContext()`
    `protected JRPropertiesHolder` | `getTextPropertiesHolder()`
    `protected java.lang.String` | `getTruncateSuffix()`
    `protected boolean` | `hasParagraphIndents()`
    `protected void` | `initialize(JRStyledText styledText, int remainingTextStart, int availableStretchHeight, boolean canOverflow)`
    `protected boolean` | `isToTruncateAtChar()`
    `JRMeasuredText` | `measure(JRStyledText styledText, int remainingTextStart, int availableStretchHeight, boolean canOverflow)` Fit a text chunk in a given space.
    `protected void` | `processLastTruncatedRow(TextLineWrapper lineWrapper, java.lang.String paragraphText, int paragraphOffset, boolean lineTruncated)`
    `protected boolean` | `renderNextLine(TextLineWrapper lineWrapper, java.util.List<java.lang.Integer> tabIndexes, int[] currentTabHolder, TabStop[] nextTabStopHolder, boolean[] requireNextWordHolder)`
    `protected boolean` | `renderParagraph(TextLineWrapper lineWrapper, int lastParagraphStart, java.lang.String lastParagraphText)`
    `protected void` | `truncateLastLineAtChar(TextLineWrapper lineWrapper, java.lang.String paragraphText, int paragraphOffset)`

    - ### Methods inherited from class java.lang.Object

      `clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait`

- - ### Field Detail

    - #### PROPERTY_MEASURE_SIMPLE_TEXTS

          public static final java.lang.String PROPERTY_MEASURE_SIMPLE_TEXTS

      See Also:
        Constant Field Values

    - #### jasperReportsContext

          protected JasperReportsContext jasperReportsContext

    - #### textElement

          protected JRCommonText textElement

    - #### width

          protected int width

    - #### leftPadding

          protected int leftPadding

    - #### rightPadding

          protected int rightPadding

    - #### maxHeight

          protected int maxHeight

    - #### measuredState

          protected TextMeasurer.TextMeasuredState measuredState

    - #### prevMeasuredState

          protected TextMeasurer.TextMeasuredState prevMeasuredState

  - ### Constructor Detail

    - #### TextMeasurer

          public TextMeasurer(JasperReportsContext jasperReportsContext,
                      JRCommonText textElement)

    - #### TextMeasurer

          public TextMeasurer(JRCommonText textElement)

      Deprecated. Replaced by `TextMeasurer(JasperReportsContext, JRCommonText)`.

  - ### Method Detail

    - #### initialize

          protected void initialize(JRStyledText styledText,
                        int remainingTextStart,
                        int availableStretchHeight,
                        boolean canOverflow)

    - #### measure

          public JRMeasuredText measure(JRStyledText styledText,
                               int remainingTextStart,
                               int availableStretchHeight,
                               boolean canOverflow)

      Description copied from interface: `JRTextMeasurer`
      Fit a text chunk in a given space.
      Specified by:
        `measure` in interface `JRTextMeasurer`
      Parameters:
        `styledText` - the full text
        `remainingTextStart` - the start index of the remaining text
        `availableStretchHeight` - the available stretch height
        `canOverflow` - whether the text element is able to overflow
      Returns:
        text measuring information

    - #### hasParagraphIndents

          protected boolean hasParagraphIndents()

    - #### renderParagraph

          protected boolean renderParagraph(TextLineWrapper lineWrapper,
                                int lastParagraphStart,
                                java.lang.String lastParagraphText)

    - #### processLastTruncatedRow

          protected void processLastTruncatedRow(TextLineWrapper lineWrapper,
                                     java.lang.String paragraphText,
                                     int paragraphOffset,
                                     boolean lineTruncated)

    - #### truncateLastLineAtChar

          protected void truncateLastLineAtChar(TextLineWrapper lineWrapper,
                                    java.lang.String paragraphText,
                                    int paragraphOffset)

    - #### appendTruncateSuffix

          protected void appendTruncateSuffix(TextLineWrapper lineWrapper)

    - #### isToTruncateAtChar

          protected boolean isToTruncateAtChar()

    - #### getTruncateSuffix

          protected java.lang.String getTruncateSuffix()

    - #### renderNextLine

          protected boolean renderNextLine(TextLineWrapper lineWrapper,
                               java.util.List<java.lang.Integer> tabIndexes,
                               int[] currentTabHolder,
                               TabStop[] nextTabStopHolder,
                               boolean[] requireNextWordHolder)

    - #### getTextPropertiesHolder

          protected JRPropertiesHolder getTextPropertiesHolder()

    - #### getFontRenderContext

          public java.awt.font.FontRenderContext getFontRenderContext()

© 2001-2010 Jaspersoft Corporation www.jaspersoft.com