| /* |
| * ==================================================================== |
| * Licensed to the Apache Software Foundation (ASF) under one or more |
| * contributor license agreements. See the NOTICE file distributed with |
| * this work for additional information regarding copyright ownership. |
| * The ASF licenses this file to You under the Apache License, Version 2.0 |
| * (the "License"); you may not use this file except in compliance with |
| * the License. You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| * ==================================================================== |
| */ |
| |
| package org.apache.poi.xslf.usermodel; |
| |
| import java.awt.Color; |
| import java.awt.geom.Rectangle2D; |
| |
| import org.apache.poi.sl.draw.DrawPaint; |
| import org.apache.poi.sl.usermodel.ColorStyle; |
| import org.apache.poi.sl.usermodel.PaintStyle; |
| import org.apache.poi.sl.usermodel.PaintStyle.SolidPaint; |
| import org.apache.poi.sl.usermodel.StrokeStyle; |
| import org.apache.poi.sl.usermodel.StrokeStyle.LineCap; |
| import org.apache.poi.sl.usermodel.StrokeStyle.LineCompound; |
| import org.apache.poi.sl.usermodel.StrokeStyle.LineDash; |
| import org.apache.poi.sl.usermodel.TableCell; |
| import org.apache.poi.sl.usermodel.VerticalAlignment; |
| import org.apache.poi.util.Units; |
| import org.apache.poi.xddf.usermodel.XDDFLineProperties; |
| import org.apache.poi.xddf.usermodel.text.XDDFTextBody; |
| import org.apache.poi.xslf.usermodel.XSLFPropertiesDelegate.XSLFFillProperties; |
| import org.apache.poi.xslf.usermodel.XSLFTableStyle.TablePartStyle; |
| import org.apache.xmlbeans.XmlObject; |
| import org.openxmlformats.schemas.drawingml.x2006.main.*; |
| |
| /** |
| * Represents a cell of a table in a .pptx presentation |
| */ |
| public class XSLFTableCell extends XSLFTextShape implements TableCell<XSLFShape, XSLFTextParagraph> { |
| private CTTableCellProperties _tcPr; |
| private final XSLFTable table; |
| private int row, col; |
| |
| /** |
| * Volatile/temporary anchor - e.g. for rendering |
| */ |
| private Rectangle2D anchor; |
| |
| /* package */ XSLFTableCell(CTTableCell cell, XSLFTable table) { |
| super(cell, table.getSheet()); |
| this.table = table; |
| } |
| |
| @Override |
| protected CTTextBody getTextBody(boolean create) { |
| CTTableCell cell = getCell(); |
| CTTextBody txBody = cell.getTxBody(); |
| if (txBody == null && create) { |
| XDDFTextBody body = new XDDFTextBody(this); |
| cell.setTxBody(body.getXmlObject()); |
| txBody = cell.getTxBody(); |
| } |
| return txBody; |
| } |
| |
| static CTTableCell prototype() { |
| CTTableCell cell = CTTableCell.Factory.newInstance(); |
| CTTableCellProperties pr = cell.addNewTcPr(); |
| pr.addNewLnL().addNewNoFill(); |
| pr.addNewLnR().addNewNoFill(); |
| pr.addNewLnT().addNewNoFill(); |
| pr.addNewLnB().addNewNoFill(); |
| return cell; |
| } |
| |
| @SuppressWarnings("WeakerAccess") |
| protected CTTableCellProperties getCellProperties(boolean create) { |
| if (_tcPr == null) { |
| CTTableCell cell = getCell(); |
| _tcPr = cell.getTcPr(); |
| if (_tcPr == null && create) { |
| _tcPr = cell.addNewTcPr(); |
| } |
| } |
| return _tcPr; |
| } |
| |
| @Override |
| public void setLeftInset(double margin) { |
| CTTableCellProperties pr = getCellProperties(true); |
| pr.setMarL(Units.toEMU(margin)); |
| } |
| |
| @Override |
| public void setRightInset(double margin) { |
| CTTableCellProperties pr = getCellProperties(true); |
| pr.setMarR(Units.toEMU(margin)); |
| } |
| |
| @Override |
| public void setTopInset(double margin) { |
| CTTableCellProperties pr = getCellProperties(true); |
| pr.setMarT(Units.toEMU(margin)); |
| } |
| |
| @Override |
| public void setBottomInset(double margin) { |
| CTTableCellProperties pr = getCellProperties(true); |
| pr.setMarB(Units.toEMU(margin)); |
| } |
| |
| private CTLineProperties getCTLine(BorderEdge edge, boolean create) { |
| if (edge == null) { |
| throw new IllegalArgumentException("BorderEdge needs to be specified."); |
| } |
| |
| CTTableCellProperties pr = getCellProperties(create); |
| if (pr == null) { |
| return null; |
| } |
| |
| switch (edge) { |
| case bottom: |
| return (pr.isSetLnB()) ? pr.getLnB() : (create ? pr.addNewLnB() : null); |
| case left: |
| return (pr.isSetLnL()) ? pr.getLnL() : (create ? pr.addNewLnL() : null); |
| case top: |
| return (pr.isSetLnT()) ? pr.getLnT() : (create ? pr.addNewLnT() : null); |
| case right: |
| return (pr.isSetLnR()) ? pr.getLnR() : (create ? pr.addNewLnR() : null); |
| default: |
| return null; |
| } |
| } |
| |
| public XDDFLineProperties getBorderProperties(BorderEdge edge) { |
| CTLineProperties props = getCTLine(edge, false); |
| return (props == null) ? null : new XDDFLineProperties(props); |
| } |
| |
| public void setBorderProperties(BorderEdge edge, XDDFLineProperties properties) { |
| CTLineProperties props = getCTLine(edge, true); |
| if (props != null) { |
| props.set(properties.getXmlObject().copy()); |
| } |
| } |
| |
| @Override |
| public void removeBorder(BorderEdge edge) { |
| CTTableCellProperties pr = getCellProperties(false); |
| if (pr == null) { |
| return; |
| } |
| switch (edge) { |
| case bottom: |
| if (pr.isSetLnB()) { |
| pr.unsetLnB(); |
| } |
| break; |
| case left: |
| if (pr.isSetLnL()) { |
| pr.unsetLnL(); |
| } |
| break; |
| case top: |
| if (pr.isSetLnT()) { |
| pr.unsetLnT(); |
| } |
| break; |
| case right: |
| if (pr.isSetLnR()) { |
| pr.unsetLnR(); |
| } |
| break; |
| default: |
| throw new IllegalArgumentException(); |
| } |
| } |
| |
| @Override |
| public StrokeStyle getBorderStyle(final BorderEdge edge) { |
| final Double width = getBorderWidth(edge); |
| return (width == null) ? null : new StrokeStyle() { |
| @Override |
| public PaintStyle getPaint() { |
| return DrawPaint.createSolidPaint(getBorderColor(edge)); |
| } |
| |
| @Override |
| public LineCap getLineCap() { |
| return getBorderCap(edge); |
| } |
| |
| @Override |
| public LineDash getLineDash() { |
| return getBorderDash(edge); |
| } |
| |
| @Override |
| public LineCompound getLineCompound() { |
| return getBorderCompound(edge); |
| } |
| |
| @Override |
| public double getLineWidth() { |
| return width; |
| } |
| }; |
| } |
| |
| @Override |
| public void setBorderStyle(BorderEdge edge, StrokeStyle style) { |
| if (style == null) { |
| throw new IllegalArgumentException("StrokeStyle needs to be specified."); |
| } |
| |
| LineCap cap = style.getLineCap(); |
| if (cap != null) { |
| setBorderCap(edge, cap); |
| } |
| |
| LineCompound compound = style.getLineCompound(); |
| if (compound != null) { |
| setBorderCompound(edge, compound); |
| } |
| |
| LineDash dash = style.getLineDash(); |
| if (dash != null) { |
| setBorderDash(edge, dash); |
| } |
| |
| double width = style.getLineWidth(); |
| setBorderWidth(edge, width); |
| } |
| |
| @SuppressWarnings("WeakerAccess") |
| public Double getBorderWidth(BorderEdge edge) { |
| CTLineProperties ln = getCTLine(edge, false); |
| return (ln == null || !ln.isSetW()) ? null : Units.toPoints(ln.getW()); |
| } |
| |
| @Override |
| public void setBorderWidth(BorderEdge edge, double width) { |
| final CTLineProperties ln = getCTLine(edge, true); |
| if (ln == null) { |
| return; |
| } |
| ln.setW(Units.toEMU(width)); |
| } |
| |
| private CTLineProperties setBorderDefaults(BorderEdge edge) { |
| final CTLineProperties ln = getCTLine(edge, true); |
| if (ln == null) { |
| throw new IllegalStateException("CTLineProperties couldn't be initialized"); |
| } |
| |
| if (ln.isSetNoFill()) { |
| ln.unsetNoFill(); |
| } |
| |
| if (!ln.isSetPrstDash()) { |
| ln.addNewPrstDash().setVal(STPresetLineDashVal.SOLID); |
| } |
| if (!ln.isSetCmpd()) { |
| ln.setCmpd(STCompoundLine.SNG); |
| } |
| if (!ln.isSetAlgn()) { |
| ln.setAlgn(STPenAlignment.CTR); |
| } |
| if (!ln.isSetCap()) { |
| ln.setCap(STLineCap.FLAT); |
| } |
| if (!ln.isSetRound()) { |
| ln.addNewRound(); |
| } |
| |
| if (!ln.isSetHeadEnd()) { |
| CTLineEndProperties hd = ln.addNewHeadEnd(); |
| hd.setType(STLineEndType.NONE); |
| hd.setW(STLineEndWidth.MED); |
| hd.setLen(STLineEndLength.MED); |
| } |
| |
| if (!ln.isSetTailEnd()) { |
| CTLineEndProperties tl = ln.addNewTailEnd(); |
| tl.setType(STLineEndType.NONE); |
| tl.setW(STLineEndWidth.MED); |
| tl.setLen(STLineEndLength.MED); |
| } |
| |
| return ln; |
| } |
| |
| @Override |
| public void setBorderColor(BorderEdge edge, Color color) { |
| if (color == null) { |
| throw new IllegalArgumentException("Colors need to be specified."); |
| } |
| |
| CTLineProperties ln = setBorderDefaults(edge); |
| CTSolidColorFillProperties fill = ln.addNewSolidFill(); |
| XSLFColor c = new XSLFColor(fill, getSheet().getTheme(), fill.getSchemeClr(), getSheet()); |
| c.setColor(color); |
| } |
| |
| @SuppressWarnings("WeakerAccess") |
| public Color getBorderColor(BorderEdge edge) { |
| CTLineProperties ln = getCTLine(edge, false); |
| if (ln == null || ln.isSetNoFill() || !ln.isSetSolidFill()) { |
| return null; |
| } |
| |
| CTSolidColorFillProperties fill = ln.getSolidFill(); |
| XSLFColor c = new XSLFColor(fill, getSheet().getTheme(), fill.getSchemeClr(), getSheet()); |
| return c.getColor(); |
| } |
| |
| @SuppressWarnings("WeakerAccess") |
| public LineCompound getBorderCompound(BorderEdge edge) { |
| CTLineProperties ln = getCTLine(edge, false); |
| if (ln == null || ln.isSetNoFill() || !ln.isSetSolidFill() || !ln.isSetCmpd()) { |
| return null; |
| } |
| |
| return LineCompound.fromOoxmlId(ln.getCmpd().intValue()); |
| } |
| |
| @Override |
| public void setBorderCompound(BorderEdge edge, LineCompound compound) { |
| if (compound == null) { |
| throw new IllegalArgumentException("LineCompound need to be specified."); |
| } |
| |
| CTLineProperties ln = setBorderDefaults(edge); |
| ln.setCmpd(STCompoundLine.Enum.forInt(compound.ooxmlId)); |
| } |
| |
| @SuppressWarnings("WeakerAccess") |
| public LineDash getBorderDash(BorderEdge edge) { |
| CTLineProperties ln = getCTLine(edge, false); |
| if (ln == null || ln.isSetNoFill() || !ln.isSetSolidFill() || !ln.isSetPrstDash()) { |
| return null; |
| } |
| |
| return LineDash.fromOoxmlId(ln.getPrstDash().getVal().intValue()); |
| } |
| |
| @Override |
| public void setBorderDash(BorderEdge edge, LineDash dash) { |
| if (dash == null) { |
| throw new IllegalArgumentException("LineDash need to be specified."); |
| } |
| |
| CTLineProperties ln = setBorderDefaults(edge); |
| if (!ln.isSetPrstDash()) { |
| ln.addNewPrstDash(); |
| } |
| ln.getPrstDash().setVal(STPresetLineDashVal.Enum.forInt(dash.ooxmlId)); |
| } |
| |
| @SuppressWarnings("WeakerAccess") |
| public LineCap getBorderCap(BorderEdge edge) { |
| CTLineProperties ln = getCTLine(edge, false); |
| if (ln == null || ln.isSetNoFill() || !ln.isSetSolidFill() || !ln.isSetCap()) { |
| return null; |
| } |
| |
| return LineCap.fromOoxmlId(ln.getCap().intValue()); |
| } |
| |
| @SuppressWarnings("WeakerAccess") |
| public void setBorderCap(BorderEdge edge, LineCap cap) { |
| if (cap == null) { |
| throw new IllegalArgumentException("LineCap need to be specified."); |
| } |
| |
| CTLineProperties ln = setBorderDefaults(edge); |
| ln.setCap(STLineCap.Enum.forInt(cap.ooxmlId)); |
| } |
| |
| /** |
| * Specifies a solid color fill. The shape is filled entirely with the |
| * specified color. |
| * |
| * @param color |
| * the solid color fill. The value of <code>null</code> unsets |
| * the solidFIll attribute from the underlying xml |
| */ |
| @Override |
| public void setFillColor(Color color) { |
| CTTableCellProperties spPr = getCellProperties(true); |
| if (color == null) { |
| if (spPr.isSetSolidFill()) { |
| spPr.unsetSolidFill(); |
| } |
| } else { |
| CTSolidColorFillProperties fill = spPr.isSetSolidFill() ? spPr.getSolidFill() : spPr.addNewSolidFill(); |
| XSLFColor c = new XSLFColor(fill, getSheet().getTheme(), fill.getSchemeClr(), getSheet()); |
| c.setColor(color); |
| } |
| } |
| |
| /** |
| * |
| * @return solid fill color of null if not set |
| */ |
| @Override |
| public Color getFillColor() { |
| PaintStyle ps = getFillPaint(); |
| if (ps instanceof SolidPaint) { |
| ColorStyle cs = ((SolidPaint) ps).getSolidColor(); |
| return DrawPaint.applyColorTransform(cs); |
| } |
| |
| return null; |
| } |
| |
| @SuppressWarnings("resource") |
| @Override |
| public PaintStyle getFillPaint() { |
| XSLFSheet sheet = getSheet(); |
| XSLFTheme theme = sheet.getTheme(); |
| final boolean hasPlaceholder = getPlaceholder() != null; |
| XmlObject props = getCellProperties(false); |
| XSLFFillProperties fp = XSLFPropertiesDelegate.getFillDelegate(props); |
| if (fp != null) { |
| PaintStyle paint = selectPaint(fp, null, sheet.getPackagePart(), theme, hasPlaceholder); |
| if (paint != null) { |
| return paint; |
| } |
| } |
| |
| CTTablePartStyle tps = getTablePartStyle(null); |
| if (tps == null || !tps.isSetTcStyle()) { |
| tps = getTablePartStyle(TablePartStyle.wholeTbl); |
| if (tps == null || !tps.isSetTcStyle()) { |
| return null; |
| } |
| } |
| |
| XMLSlideShow slideShow = sheet.getSlideShow(); |
| CTTableStyleCellStyle tcStyle = tps.getTcStyle(); |
| if (tcStyle.isSetFill()) { |
| props = tcStyle.getFill(); |
| } else if (tcStyle.isSetFillRef()) { |
| props = tcStyle.getFillRef(); |
| } else { |
| return null; |
| } |
| |
| fp = XSLFPropertiesDelegate.getFillDelegate(props); |
| if (fp != null) { |
| PaintStyle paint = selectPaint(fp, null, slideShow.getPackagePart(), theme, hasPlaceholder); |
| if (paint != null) { |
| return paint; |
| } |
| } |
| |
| return null; |
| } |
| |
| /** |
| * Retrieves the part style depending on the location of this cell |
| * |
| * @param tablePartStyle |
| * the part to be returned, usually this is null and only set |
| * when used as a helper method |
| * @return the table part style |
| */ |
| private CTTablePartStyle getTablePartStyle(TablePartStyle tablePartStyle) { |
| CTTable ct = table.getCTTable(); |
| if (!ct.isSetTblPr()) { |
| return null; |
| } |
| |
| CTTableProperties pr = ct.getTblPr(); |
| boolean bandRow = (pr.isSetBandRow() && pr.getBandRow()); |
| boolean firstRow = (pr.isSetFirstRow() && pr.getFirstRow()); |
| boolean lastRow = (pr.isSetLastRow() && pr.getLastRow()); |
| boolean bandCol = (pr.isSetBandCol() && pr.getBandCol()); |
| boolean firstCol = (pr.isSetFirstCol() && pr.getFirstCol()); |
| boolean lastCol = (pr.isSetLastCol() && pr.getLastCol()); |
| |
| TablePartStyle tps; |
| if (tablePartStyle != null) { |
| tps = tablePartStyle; |
| } else if (row == 0 && firstRow) { |
| tps = TablePartStyle.firstRow; |
| } else if (row == table.getNumberOfRows() - 1 && lastRow) { |
| tps = TablePartStyle.lastRow; |
| } else if (col == 0 && firstCol) { |
| tps = TablePartStyle.firstCol; |
| } else if (col == table.getNumberOfColumns() - 1 && lastCol) { |
| tps = TablePartStyle.lastCol; |
| } else { |
| tps = TablePartStyle.wholeTbl; |
| |
| int br = row + (firstRow ? 1 : 0); |
| int bc = col + (firstCol ? 1 : 0); |
| if (bandRow && (br & 1) == 0) { |
| tps = TablePartStyle.band1H; |
| } else if (bandCol && (bc & 1) == 0) { |
| tps = TablePartStyle.band1V; |
| } |
| } |
| |
| XSLFTableStyle tabStyle = table.getTableStyle(); |
| if (tabStyle == null) { |
| return null; |
| } |
| |
| CTTablePartStyle part = tabStyle.getTablePartStyle(tps); |
| return (part == null) ? tabStyle.getTablePartStyle(TablePartStyle.wholeTbl) : part; |
| } |
| |
| void setGridSpan(int gridSpan_) { |
| getCell().setGridSpan(gridSpan_); |
| } |
| |
| @Override |
| public int getGridSpan() { |
| CTTableCell c = getCell(); |
| return (c.isSetGridSpan()) ? c.getGridSpan() : 1; |
| } |
| |
| void setRowSpan(int rowSpan_) { |
| getCell().setRowSpan(rowSpan_); |
| } |
| |
| @Override |
| public int getRowSpan() { |
| CTTableCell c = getCell(); |
| return (c.isSetRowSpan()) ? c.getRowSpan() : 1; |
| } |
| |
| void setHMerge() { |
| getCell().setHMerge(true); |
| } |
| |
| void setVMerge() { |
| getCell().setVMerge(true); |
| } |
| |
| @Override |
| public void setVerticalAlignment(VerticalAlignment anchor) { |
| CTTableCellProperties cellProps = getCellProperties(true); |
| if (anchor == null) { |
| if (cellProps.isSetAnchor()) { |
| cellProps.unsetAnchor(); |
| } |
| } else { |
| cellProps.setAnchor(STTextAnchoringType.Enum.forInt(anchor.ordinal() + 1)); |
| } |
| } |
| |
| @Override |
| public VerticalAlignment getVerticalAlignment() { |
| CTTableCellProperties cellProps = getCellProperties(false); |
| |
| VerticalAlignment align = VerticalAlignment.TOP; |
| if (cellProps != null && cellProps.isSetAnchor()) { |
| int ival = cellProps.getAnchor().intValue(); |
| align = VerticalAlignment.values()[ival - 1]; |
| } |
| return align; |
| } |
| |
| /** |
| * @since POI 3.15-beta2 |
| */ |
| @Override |
| public void setTextDirection(TextDirection orientation) { |
| CTTableCellProperties cellProps = getCellProperties(true); |
| if (orientation == null) { |
| if (cellProps.isSetVert()) { |
| cellProps.unsetVert(); |
| } |
| } else { |
| STTextVerticalType.Enum vt; |
| switch (orientation) { |
| default: |
| case HORIZONTAL: |
| vt = STTextVerticalType.HORZ; |
| break; |
| case VERTICAL: |
| vt = STTextVerticalType.VERT; |
| break; |
| case VERTICAL_270: |
| vt = STTextVerticalType.VERT_270; |
| break; |
| case STACKED: |
| vt = STTextVerticalType.WORD_ART_VERT; |
| break; |
| } |
| |
| cellProps.setVert(vt); |
| } |
| } |
| |
| /** |
| * @since POI 3.15-beta2 |
| */ |
| @Override |
| public TextDirection getTextDirection() { |
| CTTableCellProperties cellProps = getCellProperties(false); |
| |
| STTextVerticalType.Enum orientation; |
| if (cellProps != null && cellProps.isSetVert()) { |
| orientation = cellProps.getVert(); |
| } else { |
| orientation = STTextVerticalType.HORZ; |
| } |
| |
| switch (orientation.intValue()) { |
| default: |
| case STTextVerticalType.INT_HORZ: |
| return TextDirection.HORIZONTAL; |
| case STTextVerticalType.INT_VERT: |
| case STTextVerticalType.INT_EA_VERT: |
| case STTextVerticalType.INT_MONGOLIAN_VERT: |
| return TextDirection.VERTICAL; |
| case STTextVerticalType.INT_VERT_270: |
| return TextDirection.VERTICAL_270; |
| case STTextVerticalType.INT_WORD_ART_VERT: |
| case STTextVerticalType.INT_WORD_ART_VERT_RTL: |
| return TextDirection.STACKED; |
| } |
| } |
| |
| private CTTableCell getCell() { |
| return (CTTableCell) getXmlObject(); |
| } |
| |
| /* package */ void setRowColIndex(int row, int col) { |
| this.row = row; |
| this.col = col; |
| } |
| |
| /** |
| * Return a fake-xfrm which is used for calculating the text height |
| */ |
| protected CTTransform2D getXfrm() { |
| Rectangle2D anc = getAnchor(); |
| CTTransform2D xfrm = CTTransform2D.Factory.newInstance(); |
| CTPoint2D off = xfrm.addNewOff(); |
| off.setX(Units.toEMU(anc.getX())); |
| off.setY(Units.toEMU(anc.getY())); |
| CTPositiveSize2D size = xfrm.addNewExt(); |
| size.setCx(Units.toEMU(anc.getWidth())); |
| size.setCy(Units.toEMU(anc.getHeight())); |
| return xfrm; |
| } |
| |
| /** |
| * There's no real anchor for table cells - this method is used to |
| * temporarily store the location of the cell for a later retrieval, e.g. |
| * for rendering |
| * |
| * @since POI 3.15-beta2 |
| */ |
| @Override |
| public void setAnchor(Rectangle2D anchor) { |
| if (this.anchor == null) { |
| this.anchor = (Rectangle2D) anchor.clone(); |
| } else { |
| this.anchor.setRect(anchor); |
| } |
| } |
| |
| /** |
| * @since POI 3.15-beta2 |
| */ |
| @Override |
| public Rectangle2D getAnchor() { |
| if (anchor == null) { |
| table.updateCellAnchor(); |
| } |
| // anchor should be set, after updateCellAnchor is through |
| assert (anchor != null); |
| return anchor; |
| } |
| |
| /** |
| * @since POI 3.15-beta2 |
| */ |
| @Override |
| public boolean isMerged() { |
| CTTableCell c = getCell(); |
| return (c.isSetHMerge() && c.getHMerge()) || (c.isSetVMerge() && c.getVMerge()); |
| } |
| |
| /** |
| * @since POI 3.15-beta2 |
| */ |
| @Override |
| protected XSLFCellTextParagraph newTextParagraph(CTTextParagraph p) { |
| return new XSLFCellTextParagraph(p, this); |
| } |
| |
| @Override |
| protected XmlObject getShapeProperties() { |
| return getCellProperties(false); |
| } |
| |
| /** |
| * @since POI 3.15-beta2 |
| */ |
| private final class XSLFCellTextParagraph extends XSLFTextParagraph { |
| private XSLFCellTextParagraph(CTTextParagraph p, XSLFTextShape shape) { |
| super(p, shape); |
| } |
| |
| @Override |
| protected XSLFCellTextRun newTextRun(XmlObject r) { |
| return new XSLFCellTextRun(r, this); |
| } |
| } |
| |
| /** |
| * @since POI 3.15-beta2 |
| */ |
| private final class XSLFCellTextRun extends XSLFTextRun { |
| private XSLFCellTextRun(XmlObject r, XSLFTextParagraph p) { |
| super(r, p); |
| } |
| |
| @Override |
| public PaintStyle getFontColor() { |
| CTTableStyleTextStyle txStyle = getTextStyle(); |
| if (txStyle == null) { |
| return super.getFontColor(); |
| } |
| |
| CTSchemeColor phClr = null; |
| CTFontReference fontRef = txStyle.getFontRef(); |
| if (fontRef != null) { |
| phClr = fontRef.getSchemeClr(); |
| } |
| |
| XSLFTheme theme = getSheet().getTheme(); |
| final XSLFColor c = new XSLFColor(txStyle, theme, phClr, getSheet()); |
| return DrawPaint.createSolidPaint(c.getColorStyle()); |
| } |
| |
| @Override |
| public boolean isBold() { |
| CTTableStyleTextStyle txStyle = getTextStyle(); |
| if (txStyle == null) { |
| return super.isBold(); |
| } else { |
| return txStyle.isSetB() && txStyle.getB().intValue() == STOnOffStyleType.INT_ON; |
| } |
| } |
| |
| @Override |
| public boolean isItalic() { |
| CTTableStyleTextStyle txStyle = getTextStyle(); |
| if (txStyle == null) { |
| return super.isItalic(); |
| } else { |
| return txStyle.isSetI() && txStyle.getI().intValue() == STOnOffStyleType.INT_ON; |
| } |
| } |
| |
| private CTTableStyleTextStyle getTextStyle() { |
| CTTablePartStyle tps = getTablePartStyle(null); |
| if (tps == null || !tps.isSetTcTxStyle()) { |
| tps = getTablePartStyle(TablePartStyle.wholeTbl); |
| } |
| return (tps == null) ? null : tps.getTcTxStyle(); |
| } |
| } |
| } |