package net.sf.jasperreports.engine.fill; import java.awt.Color; import java.awt.font.TextAttribute; import java.util.HashMap; import java.util.Map; import net.sf.jasperreports.engine.JRAlignment; import net.sf.jasperreports.engine.JRBox; import net.sf.jasperreports.engine.JRBoxContainer; import net.sf.jasperreports.engine.JRCommonElement; import net.sf.jasperreports.engine.JRCommonText; import net.sf.jasperreports.engine.JRElement; import net.sf.jasperreports.engine.JRException; import net.sf.jasperreports.engine.JRFont; import net.sf.jasperreports.engine.JRLineBox; import net.sf.jasperreports.engine.JRPen; import net.sf.jasperreports.engine.JRPrintText; import net.sf.jasperreports.engine.JRPropertiesHolder; import net.sf.jasperreports.engine.JRReportFont; import net.sf.jasperreports.engine.JRRuntimeException; import net.sf.jasperreports.engine.JRStyle; import net.sf.jasperreports.engine.JRTextElement; import net.sf.jasperreports.engine.util.JRFontUtil; import net.sf.jasperreports.engine.util.JRPenUtil; import net.sf.jasperreports.engine.util.JRProperties; import net.sf.jasperreports.engine.util.JRSingletonCache; import net.sf.jasperreports.engine.util.JRStringUtil; import net.sf.jasperreports.engine.util.JRStyleResolver; import net.sf.jasperreports.engine.util.JRStyledText; import net.sf.jasperreports.engine.util.JRTextMeasurerUtil; import net.sf.jasperreports.engine.util.LineBoxWrapper; import net.sf.jasperreports.engine.util.MarkupProcessor; import net.sf.jasperreports.engine.util.MarkupProcessorFactory; public abstract class JRFillTextElement extends JRFillElement implements JRTextElement { private static final JRSingletonCache markupProcessorFactoryCache = new JRSingletonCache(MarkupProcessorFactory.class); private static final Map markupProcessors = new HashMap(); private boolean isLeftToRight = true; private JRTextMeasurer textMeasurer = null; private float lineSpacingFactor = 0.0F; private float leadingOffset = 0.0F; private float textHeight = 0.0F; private int textStart = 0; private int textEnd = 0; private String textTruncateSuffix; private String rawText = null; private JRStyledText styledText = null; private Map styledTextAttributesMap = new HashMap(); protected final JRReportFont reportFont; protected JRFillTextElement(JRBaseFiller filler, JRTextElement textElement, JRFillObjectFactory factory) { super(filler, (JRElement)textElement, factory); this.reportFont = factory.getReportFont(textElement.getReportFont()); } protected JRFillTextElement(JRFillTextElement textElement, JRFillCloneFactory factory) { super(textElement, factory); this.reportFont = textElement.reportFont; } private void createTextMeasurer() { this.textMeasurer = JRTextMeasurerUtil.createTextMeasurer((JRCommonText)this); } protected void ensureTextMeasurer() { if (this.textMeasurer == null) createTextMeasurer(); } public byte getMode() { return JRStyleResolver.getMode((JRCommonElement)this, (byte)2); } public byte getTextAlignment() { return JRStyleResolver.getHorizontalAlignment((JRAlignment)this); } public void setTextAlignment(byte horizontalAlignment) {} public byte getHorizontalAlignment() { return JRStyleResolver.getHorizontalAlignment((JRAlignment)this); } public Byte getOwnHorizontalAlignment() { return ((JRTextElement)this.parent).getOwnHorizontalAlignment(); } public void setHorizontalAlignment(byte horizontalAlignment) {} public void setHorizontalAlignment(Byte horizontalAlignment) {} public byte getVerticalAlignment() { return JRStyleResolver.getVerticalAlignment((JRAlignment)this); } public Byte getOwnVerticalAlignment() { return ((JRTextElement)this.parent).getOwnVerticalAlignment(); } public void setVerticalAlignment(byte verticalAlignment) {} public void setVerticalAlignment(Byte verticalAlignment) {} public byte getRotation() { return JRStyleResolver.getRotation((JRCommonText)this); } public Byte getOwnRotation() { return ((JRTextElement)this.parent).getOwnRotation(); } public void setRotation(byte rotation) {} public void setRotation(Byte rotation) {} public byte getLineSpacing() { return JRStyleResolver.getLineSpacing((JRCommonText)this); } public Byte getOwnLineSpacing() { return ((JRTextElement)this.parent).getOwnLineSpacing(); } public void setLineSpacing(byte lineSpacing) {} public void setLineSpacing(Byte lineSpacing) {} public boolean isStyledText() { return "styled".equals(getMarkup()); } public Boolean isOwnStyledText() { String mkp = getOwnMarkup(); return "styled".equals(mkp) ? Boolean.TRUE : ((mkp == null) ? null : Boolean.FALSE); } public void setStyledText(boolean isStyledText) {} public void setStyledText(Boolean isStyledText) {} public String getMarkup() { return JRStyleResolver.getMarkup((JRCommonText)this); } public String getOwnMarkup() { return ((JRTextElement)this.parent).getOwnMarkup(); } public void setMarkup(String markup) {} public JRBox getBox() { return (JRBox)new LineBoxWrapper(getLineBox()); } public JRLineBox getLineBox() { return ((JRBoxContainer)this.parent).getLineBox(); } public byte getBorder() { return JRPenUtil.getPenFromLinePen((JRPen)getLineBox().getPen()); } public Byte getOwnBorder() { return JRPenUtil.getOwnPenFromLinePen((JRPen)getLineBox().getPen()); } public void setBorder(byte border) { JRPenUtil.setLinePenFromPen(border, (JRPen)getLineBox().getPen()); } public void setBorder(Byte border) { JRPenUtil.setLinePenFromPen(border, (JRPen)getLineBox().getPen()); } public Color getBorderColor() { return getLineBox().getPen().getLineColor(); } public Color getOwnBorderColor() { return getLineBox().getPen().getOwnLineColor(); } public void setBorderColor(Color borderColor) { getLineBox().getPen().setLineColor(borderColor); } public int getPadding() { return getLineBox().getPadding().intValue(); } public Integer getOwnPadding() { return getLineBox().getOwnPadding(); } public void setPadding(int padding) { getLineBox().setPadding(padding); } public void setPadding(Integer padding) { getLineBox().setPadding(padding); } public byte getTopBorder() { return JRPenUtil.getPenFromLinePen((JRPen)getLineBox().getTopPen()); } public Byte getOwnTopBorder() { return JRPenUtil.getOwnPenFromLinePen((JRPen)getLineBox().getTopPen()); } public void setTopBorder(byte topBorder) { JRPenUtil.setLinePenFromPen(topBorder, (JRPen)getLineBox().getTopPen()); } public void setTopBorder(Byte topBorder) { JRPenUtil.setLinePenFromPen(topBorder, (JRPen)getLineBox().getTopPen()); } public Color getTopBorderColor() { return getLineBox().getTopPen().getLineColor(); } public Color getOwnTopBorderColor() { return getLineBox().getTopPen().getOwnLineColor(); } public void setTopBorderColor(Color topBorderColor) { getLineBox().getTopPen().setLineColor(topBorderColor); } public int getTopPadding() { return getLineBox().getTopPadding().intValue(); } public Integer getOwnTopPadding() { return getLineBox().getOwnTopPadding(); } public void setTopPadding(int topPadding) { getLineBox().setTopPadding(topPadding); } public void setTopPadding(Integer topPadding) { getLineBox().setTopPadding(topPadding); } public byte getLeftBorder() { return JRPenUtil.getPenFromLinePen((JRPen)getLineBox().getLeftPen()); } public Byte getOwnLeftBorder() { return JRPenUtil.getOwnPenFromLinePen((JRPen)getLineBox().getLeftPen()); } public void setLeftBorder(byte leftBorder) { JRPenUtil.setLinePenFromPen(leftBorder, (JRPen)getLineBox().getLeftPen()); } public void setLeftBorder(Byte leftBorder) { JRPenUtil.setLinePenFromPen(leftBorder, (JRPen)getLineBox().getLeftPen()); } public Color getLeftBorderColor() { return getLineBox().getLeftPen().getLineColor(); } public Color getOwnLeftBorderColor() { return getLineBox().getLeftPen().getOwnLineColor(); } public void setLeftBorderColor(Color leftBorderColor) { getLineBox().getLeftPen().setLineColor(leftBorderColor); } public int getLeftPadding() { return getLineBox().getLeftPadding().intValue(); } public Integer getOwnLeftPadding() { return getLineBox().getOwnLeftPadding(); } public void setLeftPadding(int leftPadding) { getLineBox().setLeftPadding(leftPadding); } public void setLeftPadding(Integer leftPadding) { getLineBox().setLeftPadding(leftPadding); } public byte getBottomBorder() { return JRPenUtil.getPenFromLinePen((JRPen)getLineBox().getBottomPen()); } public Byte getOwnBottomBorder() { return JRPenUtil.getOwnPenFromLinePen((JRPen)getLineBox().getBottomPen()); } public void setBottomBorder(byte bottomBorder) { JRPenUtil.setLinePenFromPen(bottomBorder, (JRPen)getLineBox().getBottomPen()); } public void setBottomBorder(Byte bottomBorder) { JRPenUtil.setLinePenFromPen(bottomBorder, (JRPen)getLineBox().getBottomPen()); } public Color getBottomBorderColor() { return getLineBox().getBottomPen().getLineColor(); } public Color getOwnBottomBorderColor() { return getLineBox().getBottomPen().getOwnLineColor(); } public void setBottomBorderColor(Color bottomBorderColor) { getLineBox().getBottomPen().setLineColor(bottomBorderColor); } public int getBottomPadding() { return getLineBox().getBottomPadding().intValue(); } public Integer getOwnBottomPadding() { return getLineBox().getOwnBottomPadding(); } public void setBottomPadding(int bottomPadding) { getLineBox().setBottomPadding(bottomPadding); } public void setBottomPadding(Integer bottomPadding) { getLineBox().setBottomPadding(bottomPadding); } public byte getRightBorder() { return JRPenUtil.getPenFromLinePen((JRPen)getLineBox().getRightPen()); } public Byte getOwnRightBorder() { return JRPenUtil.getOwnPenFromLinePen((JRPen)getLineBox().getRightPen()); } public void setRightBorder(byte rightBorder) { JRPenUtil.setLinePenFromPen(rightBorder, (JRPen)getLineBox().getRightPen()); } public void setRightBorder(Byte rightBorder) { JRPenUtil.setLinePenFromPen(rightBorder, (JRPen)getLineBox().getRightPen()); } public Color getRightBorderColor() { return getLineBox().getRightPen().getLineColor(); } public Color getOwnRightBorderColor() { return getLineBox().getRightPen().getOwnLineColor(); } public void setRightBorderColor(Color rightBorderColor) { getLineBox().getRightPen().setLineColor(rightBorderColor); } public int getRightPadding() { return getLineBox().getRightPadding().intValue(); } public Integer getOwnRightPadding() { return getLineBox().getOwnRightPadding(); } public void setRightPadding(int rightPadding) { getLineBox().setRightPadding(rightPadding); } public void setRightPadding(Integer rightPadding) { getLineBox().setRightPadding(rightPadding); } public JRFont getFont() { return (JRFont)this; } protected Map getStyledTextAttributes() { JRStyle style = getStyle(); Map styledTextAttributes = (Map)this.styledTextAttributesMap.get(style); if (styledTextAttributes == null) { styledTextAttributes = new HashMap(); JRFontUtil.setAttributes(styledTextAttributes, (JRFont)this); styledTextAttributes.put(TextAttribute.FOREGROUND, getForecolor()); if (getMode() == 1) styledTextAttributes.put(TextAttribute.BACKGROUND, getBackcolor()); this.styledTextAttributesMap.put(style, styledTextAttributes); } return styledTextAttributes; } protected float getLineSpacingFactor() { return this.lineSpacingFactor; } protected void setLineSpacingFactor(float lineSpacingFactor) { this.lineSpacingFactor = lineSpacingFactor; } protected float getLeadingOffset() { return this.leadingOffset; } protected void setLeadingOffset(float leadingOffset) { this.leadingOffset = leadingOffset; } protected byte getRunDirection() { return this.isLeftToRight ? 0 : 1; } protected float getTextHeight() { return this.textHeight; } protected void setTextHeight(float textHeight) { this.textHeight = textHeight; } protected int getTextStart() { return this.textStart; } protected void setTextStart(int textStart) { this.textStart = textStart; } protected int getTextEnd() { return this.textEnd; } protected void setTextEnd(int textEnd) { this.textEnd = textEnd; } protected String getRawText() { return this.rawText; } protected void setRawText(String rawText) { this.rawText = rawText; this.styledText = null; } protected void reset() { super.reset(); this.isLeftToRight = true; this.lineSpacingFactor = 0.0F; this.leadingOffset = 0.0F; this.textHeight = 0.0F; } protected void rewind() { this.textStart = 0; this.textEnd = 0; } protected JRStyledText getStyledText() { if (this.styledText == null) { String text = getRawText(); if (text != null) this.styledText = this.filler.getStyledTextParser().getStyledText(getStyledTextAttributes(), text, !"none".equals(getMarkup())); } return this.styledText; } public String getText() { JRStyledText tmpStyledText = getStyledText(); if (tmpStyledText == null) return null; return tmpStyledText.getText(); } protected void chopTextElement(int availableStretchHeight) { ensureTextMeasurer(); JRStyledText tmpStyledText = getStyledText(); if (tmpStyledText == null) return; if (getTextEnd() == tmpStyledText.getText().length()) return; JRMeasuredText measuredText = this.textMeasurer.measure(tmpStyledText, getTextEnd(), availableStretchHeight, canOverflow()); this.isLeftToRight = measuredText.isLeftToRight(); setTextHeight(measuredText.getTextHeight()); if (getRotation() == 0) { setStretchHeight((int)getTextHeight() + getLineBox().getTopPadding().intValue() + getLineBox().getBottomPadding().intValue()); } else { setStretchHeight(getHeight()); } setTextStart(getTextEnd()); setTextEnd(measuredText.getTextOffset()); setTextTruncateSuffix(measuredText.getTextSuffix()); setLineSpacingFactor(measuredText.getLineSpacingFactor()); setLeadingOffset(measuredText.getLeadingOffset()); } public JRReportFont getReportFont() { return this.reportFont; } public void setReportFont(JRReportFont reportFont) {} public String getFontName() { return JRStyleResolver.getFontName((JRFont)this); } public String getOwnFontName() { return ((JRFont)this.parent).getOwnFontName(); } public void setFontName(String fontName) {} public boolean isBold() { return JRStyleResolver.isBold((JRFont)this); } public Boolean isOwnBold() { return ((JRFont)this.parent).isOwnBold(); } public void setBold(boolean isBold) {} public void setBold(Boolean isBold) {} public boolean isItalic() { return JRStyleResolver.isItalic((JRFont)this); } public Boolean isOwnItalic() { return ((JRFont)this.parent).isOwnItalic(); } public void setItalic(boolean isItalic) {} public void setItalic(Boolean isItalic) {} public boolean isUnderline() { return JRStyleResolver.isUnderline((JRFont)this); } public Boolean isOwnUnderline() { return ((JRFont)this.parent).isOwnUnderline(); } public void setUnderline(boolean isUnderline) {} public void setUnderline(Boolean isUnderline) {} public boolean isStrikeThrough() { return JRStyleResolver.isStrikeThrough((JRFont)this); } public Boolean isOwnStrikeThrough() { return ((JRFont)this.parent).isOwnStrikeThrough(); } public void setStrikeThrough(boolean isStrikeThrough) {} public void setStrikeThrough(Boolean isStrikeThrough) {} public int getFontSize() { return JRStyleResolver.getFontSize((JRFont)this); } public Integer getOwnFontSize() { return ((JRFont)this.parent).getOwnFontSize(); } public void setFontSize(int size) {} public void setFontSize(Integer size) {} public int getSize() { return getFontSize(); } public Integer getOwnSize() { return getOwnFontSize(); } public void setSize(int size) {} public void setSize(Integer size) {} public String getPdfFontName() { return JRStyleResolver.getPdfFontName((JRFont)this); } public String getOwnPdfFontName() { return ((JRFont)this.parent).getOwnPdfFontName(); } public void setPdfFontName(String pdfFontName) {} public String getPdfEncoding() { return JRStyleResolver.getPdfEncoding((JRFont)this); } public String getOwnPdfEncoding() { return ((JRFont)this.parent).getOwnPdfEncoding(); } public void setPdfEncoding(String pdfEncoding) {} public boolean isPdfEmbedded() { return JRStyleResolver.isPdfEmbedded((JRFont)this); } public Boolean isOwnPdfEmbedded() { return ((JRFont)this.parent).isOwnPdfEmbedded(); } public void setPdfEmbedded(boolean isPdfEmbedded) { setPdfEmbedded(isPdfEmbedded ? Boolean.TRUE : Boolean.FALSE); } public void setPdfEmbedded(Boolean isPdfEmbedded) {} public Color getDefaultLineColor() { return getForecolor(); } public void setHeight(int height) { super.setHeight(height); createTextMeasurer(); } public void setWidth(int width) { super.setWidth(width); createTextMeasurer(); } protected String processMarkupText(String text) { text = JRStringUtil.replaceCRwithLF(text); if (text != null) { String markup = getMarkup(); if (!"none".equals(markup) && !"styled".equals(markup)) text = getMarkupProcessor(markup).convert(text); } return text; } protected static MarkupProcessor getMarkupProcessor(String markup) { MarkupProcessor markupProcessor = (MarkupProcessor)markupProcessors.get(markup); if (markupProcessor == null) { String factoryClass = JRProperties.getProperty("net.sf.jasperreports.markup.processor.factory." + markup); if (factoryClass == null) throw new JRRuntimeException("No markup processor factory specifyed for '" + markup + "' markup."); MarkupProcessorFactory factory = null; try { factory = (MarkupProcessorFactory)markupProcessorFactoryCache.getCachedInstance(factoryClass); } catch (JRException e) { throw new JRRuntimeException(e); } markupProcessor = factory.createMarkupProcessor(); markupProcessors.put(markup, markupProcessor); } return markupProcessor; } protected void setPrintText(JRPrintText printText) { int startIndex = getTextStart(); int endIndex = getTextEnd(); JRStyledText fullStyledText = getStyledText(); String fullText = fullStyledText.getText(); boolean keepAllText = (!canOverflow() && JRProperties.getBooleanProperty((JRPropertiesHolder)this, "net.sf.jasperreports.print.keep.full.text", false)); if (keepAllText) { if (startIndex != 0) throw new JRRuntimeException("Text start index != 0 on keep all text."); if (!"none".equals(getMarkup())) { String styledText = this.filler.getStyledTextParser().write(fullStyledText); printText.setText(styledText); } else { printText.setText(fullText); } if (endIndex < fullText.length()) printText.setTextTruncateIndex(new Integer(endIndex)); } else { String printedText; if (!"none".equals(getMarkup())) { printedText = this.filler.getStyledTextParser().write(fullStyledText, startIndex, endIndex); } else { printedText = fullText.substring(startIndex, endIndex); } printText.setText(printedText); } printText.setTextTruncateSuffix(getTextTruncateSuffix()); } protected String getTextTruncateSuffix() { return this.textTruncateSuffix; } protected void setTextTruncateSuffix(String textTruncateSuffix) { this.textTruncateSuffix = textTruncateSuffix; } protected abstract boolean canOverflow(); }