
com.itextpdf.tool.xml.css.apply.HtmlCellCssApplier Maven / Gradle / Ivy
/*
*
* This file is part of the iText (R) project.
Copyright (c) 1998-2022 iText Group NV
* Authors: Balder Van Camp, Emiel Ackermann, et al.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License version 3
* as published by the Free Software Foundation with the addition of the
* following permission added to Section 15 as permitted in Section 7(a):
* FOR ANY PART OF THE COVERED WORK IN WHICH THE COPYRIGHT IS OWNED BY
* ITEXT GROUP. ITEXT GROUP DISCLAIMS THE WARRANTY OF NON INFRINGEMENT
* OF THIRD PARTY RIGHTS
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Affero General Public License for more details.
* You should have received a copy of the GNU Affero General Public License
* along with this program; if not, see http://www.gnu.org/licenses or write to
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
* Boston, MA, 02110-1301 USA, or download the license from the following URL:
* http://itextpdf.com/terms-of-use/
*
* The interactive user interfaces in modified source and object code versions
* of this program must display Appropriate Legal Notices, as required under
* Section 5 of the GNU Affero General Public License.
*
* In accordance with Section 7(b) of the GNU Affero General Public License,
* a covered work must retain the producer line in every PDF that is created
* or manipulated using iText.
*
* You can be released from the requirements of the license by purchasing
* a commercial license. Buying such a license is mandatory as soon as you
* develop commercial activities involving the iText software without
* disclosing the source code of your own applications.
* These activities include: offering paid services to customers as an ASP,
* serving PDFs on the fly in a web application, shipping iText with a closed
* source product.
*
* For more information, please contact iText Software Corp. at this
* address: [email protected]
*/
package com.itextpdf.tool.xml.css.apply;
import com.itextpdf.text.BaseColor;
import com.itextpdf.text.Element;
import com.itextpdf.text.PageSize;
import com.itextpdf.text.Rectangle;
import com.itextpdf.text.html.HtmlUtilities;
import com.itextpdf.tool.xml.Tag;
import com.itextpdf.tool.xml.css.CSS;
import com.itextpdf.tool.xml.css.CssUtils;
import com.itextpdf.tool.xml.css.HeightCalculator;
import com.itextpdf.tool.xml.css.WidthCalculator;
import com.itextpdf.tool.xml.html.CssApplier;
import com.itextpdf.tool.xml.html.HTML;
import com.itextpdf.tool.xml.html.pdfelement.HtmlCell;
import com.itextpdf.tool.xml.html.table.CellSpacingEvent;
import com.itextpdf.tool.xml.html.table.Table;
import com.itextpdf.tool.xml.html.table.TableStyleValues;
import com.itextpdf.tool.xml.pipeline.html.HtmlPipelineContext;
import java.util.Map;
import java.util.Map.Entry;
/**
* @author Emiel Ackermann
*
*/
public class HtmlCellCssApplier implements CssApplier {
private final CssUtils utils = CssUtils.getInstance();
/**
* Applies css to a HtmlCell
*
* @param cell the HtmlCell
* @param t the tag with the styles
* @param memory current margin memory
* @param psc the {@link PageSize} container
* @return a styled HtmlCell
*/
public HtmlCell apply(final HtmlCell cell, final Tag t, final MarginMemory memory, final PageSizeContainable psc) {
return apply(cell, t, memory, psc, null);
}
public HtmlCell apply(final HtmlCell cell, final Tag t, final MarginMemory memory, final PageSizeContainable psc, final HtmlPipelineContext ctx) {
Tag row = t.getParent();
while(row != null && !row.getName().equals(HTML.Tag.TR)){
row = row.getParent();
}
Tag table = t.getParent();
while(table!= null && !table.getName().equals(HTML.Tag.TABLE)){
table = table.getParent();
}
final TableStyleValues values = Table.setBorderAttributeForCell(table);
Map css = t.getCSS();
String emptyCells = css.get(CSS.Property.EMPTY_CELLS);
if(null != emptyCells && CSS.Value.HIDE.equalsIgnoreCase(emptyCells) && cell.getCompositeElements() == null) {
cell.setBorder(Rectangle.NO_BORDER);
} else {
cell.setVerticalAlignment(Element.ALIGN_MIDDLE); // Default css behavior. Implementation of "vertical-align" style further along.
String vAlign = null;
if (t.getAttributes().containsKey(HTML.Attribute.VALIGN)) {
vAlign = t.getAttributes().get(HTML.Attribute.VALIGN);
} else if (css.containsKey(HTML.Attribute.VALIGN)) {
vAlign = css.get(HTML.Attribute.VALIGN);
} else if (row != null) {
if (row.getAttributes().containsKey(HTML.Attribute.VALIGN)) {
vAlign = row.getAttributes().get(HTML.Attribute.VALIGN);
} else if (row.getCSS().containsKey(HTML.Attribute.VALIGN)) {
vAlign = row.getCSS().get(HTML.Attribute.VALIGN);
}
}
if (vAlign != null) {
if (vAlign.equalsIgnoreCase(CSS.Value.TOP)) {
cell.setVerticalAlignment(Element.ALIGN_TOP);
} else if (vAlign.equalsIgnoreCase(CSS.Value.BOTTOM)) {
cell.setVerticalAlignment(Element.ALIGN_BOTTOM);
}
}
String align = null;
if (t.getAttributes().containsKey(HTML.Attribute.ALIGN)) {
align = t.getAttributes().get(HTML.Attribute.ALIGN);
} else if (css.containsKey(CSS.Property.TEXT_ALIGN)) {
align = css.get(CSS.Property.TEXT_ALIGN);
}
if (align != null) {
if (align.equalsIgnoreCase(CSS.Value.CENTER)) {
cell.setHorizontalAlignment(Element.ALIGN_CENTER);
} else if (align.equalsIgnoreCase(CSS.Value.RIGHT)) {
cell.setHorizontalAlignment(Element.ALIGN_RIGHT);
} else if (align.equalsIgnoreCase(CSS.Value.JUSTIFY)) {
cell.setHorizontalAlignment(Element.ALIGN_JUSTIFIED);
}
}
if(t.getAttributes().get(HTML.Attribute.WIDTH) != null || css.get(HTML.Attribute.WIDTH) != null) {
cell.setFixedWidth(new WidthCalculator().getWidth(t, memory.getRootTags(), psc.getPageSize().getWidth()));
}
HeightCalculator heightCalc = new HeightCalculator();
Float height = heightCalc.getHeight(t, psc.getPageSize().getHeight());
if (height == null && row != null) {
height = heightCalc.getHeight(row, psc.getPageSize().getHeight());
}
if (height != null) {
cell.setMinimumHeight(height);
}
String colspan = t.getAttributes().get(HTML.Attribute.COLSPAN);
if (null != colspan) {
cell.setColspan(Integer.parseInt(colspan));
}
String rowspan = t.getAttributes().get(HTML.Attribute.ROWSPAN);
if (null != rowspan) {
cell.setRowspan(Integer.parseInt(rowspan));
}
for (Entry entry : css.entrySet()) {
String key = entry.getKey();
String value = entry.getValue();
cell.setUseBorderPadding(true);
if(key.equalsIgnoreCase(CSS.Property.BACKGROUND_COLOR)) {
values.setBackground(HtmlUtilities.decodeColor(value));
} else if(key.equalsIgnoreCase(CSS.Property.VERTICAL_ALIGN)) {
if(value.equalsIgnoreCase(CSS.Value.TOP)) {
cell.setVerticalAlignment(Element.ALIGN_TOP);
cell.setPaddingTop(cell.getPaddingTop()+6);
} else if(value.equalsIgnoreCase(CSS.Value.BOTTOM)) {
cell.setVerticalAlignment(Element.ALIGN_BOTTOM);
cell.setPaddingBottom(cell.getPaddingBottom()+6);
}
} else if(key.contains(CSS.Property.BORDER)) {
if(key.contains(CSS.Value.TOP)) {
setTopOfBorder(cell, key, value, values);
} else if(key.contains(CSS.Value.BOTTOM)) {
setBottomOfBorder(cell, key, value, values);
} else if(key.contains(CSS.Value.LEFT)) {
setLeftOfBorder(cell, key, value, values);
} else if(key.contains(CSS.Value.RIGHT)) {
setRightOfBorder(cell, key, value, values);
}
} else if(key.contains(CSS.Property.CELLPADDING) || key.contains(CSS.Property.PADDING)) {
if(key.contains(CSS.Value.TOP)) {
cell.setPaddingTop(cell.getPaddingTop()+utils.parsePxInCmMmPcToPt(value));
} else if(key.contains(CSS.Value.BOTTOM)) {
cell.setPaddingBottom(cell.getPaddingBottom()+utils.parsePxInCmMmPcToPt(value));
} else if(key.contains(CSS.Value.LEFT)) {
cell.setPaddingLeft(cell.getPaddingLeft()+utils.parsePxInCmMmPcToPt(value));
} else if(key.contains(CSS.Value.RIGHT)) {
cell.setPaddingRight(cell.getPaddingRight()+utils.parsePxInCmMmPcToPt(value));
}
} else if(key.contains(CSS.Property.TEXT_ALIGN)) {
cell.setHorizontalAlignment(CSS.getElementAlignment(value));
}
}
cell.setPaddingLeft(cell.getPaddingLeft() + values.getHorBorderSpacing() + values.getBorderWidthLeft());
cell.setPaddingRight(cell.getPaddingRight() + values.getBorderWidthRight());
cell.setPaddingTop(cell.getPaddingTop() + values.getVerBorderSpacing() + values.getBorderWidthTop());
cell.setPaddingBottom(cell.getPaddingBottom() + values.getBorderWidthBottom());
}
cell.setBorder(Rectangle.NO_BORDER);
cell.setCellEvent(new CellSpacingEvent(values));
cell.setCellValues(values);
return cell;
}
private void setTopOfBorder(final HtmlCell cell, final String key, final String value, final TableStyleValues values) {
if(key.contains(CSS.Property.WIDTH)) {
values.setBorderWidthTop(utils.parsePxInCmMmPcToPt(value));
}
if(key.contains(CSS.Property.COLOR)) {
values.setBorderColorTop(HtmlUtilities.decodeColor(value));
} else if(values.getBorderColorTop() == null){
values.setBorderColorTop(BaseColor.BLACK);
}
if(key.contains("style")) {
// If any, which are the border styles in iText? simulate in the borderevent?
if(values.getBorderWidthTop(false) == null){
values.setBorderWidthTop(2.25f);
}
}
}
private void setBottomOfBorder(final HtmlCell cell, final String key, final String value, final TableStyleValues values) {
if(key.contains(CSS.Property.WIDTH)) {
values.setBorderWidthBottom(utils.parsePxInCmMmPcToPt(value));
}
if(key.contains(CSS.Property.COLOR)) {
values.setBorderColorBottom(HtmlUtilities.decodeColor(value));
} else if(values.getBorderColorBottom() == null){
values.setBorderColorBottom(BaseColor.BLACK);
}
if(key.contains("style")) {
// If any, which are the border styles in iText? simulate in the borderevent?
if(values.getBorderWidthBottom(false) == null){
values.setBorderWidthBottom(2.25f);
}
}
}
private void setLeftOfBorder(final HtmlCell cell, final String key, final String value, final TableStyleValues values) {
if(key.contains(CSS.Property.WIDTH)) {
values.setBorderWidthLeft(utils.parsePxInCmMmPcToPt(value));
}
if(key.contains(CSS.Property.COLOR)) {
values.setBorderColorLeft(HtmlUtilities.decodeColor(value));
} else if(values.getBorderColorLeft() == null){
values.setBorderColorLeft(BaseColor.BLACK);
}
if(key.contains("style")) {
// If any, which are the border styles in iText? simulate in the borderevent?
if(values.getBorderWidthLeft(false) == null){
values.setBorderWidthLeft(2.25f);
}
}
}
private void setRightOfBorder(final HtmlCell cell, final String key, final String value, final TableStyleValues values) {
if(key.contains(CSS.Property.WIDTH)) {
values.setBorderWidthRight(utils.parsePxInCmMmPcToPt(value));
}
if(key.contains(CSS.Property.COLOR)) {
values.setBorderColorRight(HtmlUtilities.decodeColor(value));
} else if(values.getBorderColorRight() == null){
values.setBorderColorRight(BaseColor.BLACK);
}
if(key.contains("style")) {
// If any, which are the border styles in iText? simulate in the borderevent?
if(values.getBorderWidthRight(false) == null){
values.setBorderWidthRight(2.25f);
}
}
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy