Вы не можете выбрать более 25 тем Темы должны начинаться с буквы или цифры, могут содержать дефисы(-) и должны содержать не более 35 символов.

XSLFChart.java 7.9KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227
  1. /*
  2. * ====================================================================
  3. * Licensed to the Apache Software Foundation (ASF) under one or more
  4. * contributor license agreements. See the NOTICE file distributed with
  5. * this work for additional information regarding copyright ownership.
  6. * The ASF licenses this file to You under the Apache License, Version 2.0
  7. * (the "License"); you may not use this file except in compliance with
  8. * the License. You may obtain a copy of the License at
  9. *
  10. * http://www.apache.org/licenses/LICENSE-2.0
  11. *
  12. * Unless required by applicable law or agreed to in writing, software
  13. * distributed under the License is distributed on an "AS IS" BASIS,
  14. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  15. * See the License for the specific language governing permissions and
  16. * limitations under the License.
  17. * ====================================================================
  18. */
  19. package org.apache.poi.xslf.usermodel;
  20. import static org.apache.poi.POIXMLTypeLoader.DEFAULT_XML_OPTIONS;
  21. import java.io.IOException;
  22. import java.io.OutputStream;
  23. import javax.xml.namespace.QName;
  24. import org.apache.poi.POIXMLDocument;
  25. import org.apache.poi.POIXMLDocumentPart;
  26. import org.apache.poi.POIXMLException;
  27. import org.apache.poi.POIXMLRelation;
  28. import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
  29. import org.apache.poi.openxml4j.exceptions.NotOfficeXmlFileException;
  30. import org.apache.poi.openxml4j.opc.PackagePart;
  31. import org.apache.poi.ss.util.CellRangeAddress;
  32. import org.apache.poi.ss.util.CellReference;
  33. import org.apache.poi.util.Beta;
  34. import org.apache.poi.xddf.usermodel.chart.XDDFChart;
  35. import org.apache.poi.xddf.usermodel.chart.XDDFChartData;
  36. import org.apache.poi.xddf.usermodel.chart.XDDFDataSource;
  37. import org.apache.poi.xddf.usermodel.chart.XDDFNumericalDataSource;
  38. import org.apache.poi.xssf.usermodel.XSSFRow;
  39. import org.apache.poi.xssf.usermodel.XSSFSheet;
  40. import org.apache.poi.xssf.usermodel.XSSFWorkbook;
  41. import org.apache.xmlbeans.XmlException;
  42. import org.apache.xmlbeans.XmlOptions;
  43. import org.openxmlformats.schemas.drawingml.x2006.chart.CTChartSpace;
  44. import org.openxmlformats.schemas.drawingml.x2006.chart.CTTitle;
  45. import org.openxmlformats.schemas.drawingml.x2006.main.CTTextBody;
  46. /**
  47. * Represents a Chart in a .pptx presentation
  48. *
  49. *
  50. */
  51. @Beta
  52. public final class XSLFChart extends XDDFChart {
  53. protected static final POIXMLRelation WORKBOOK_RELATIONSHIP = new POIXMLRelation(
  54. "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",
  55. POIXMLDocument.PACK_OBJECT_REL_TYPE,
  56. "/ppt/embeddings/Microsoft_Excel_Worksheet#.xlsx",
  57. XSSFWorkbook.class
  58. ){};
  59. /**
  60. * Underlying workbook
  61. */
  62. private XSSFWorkbook workbook;
  63. /**
  64. * Construct a PresentationML chart.
  65. */
  66. protected XSLFChart() {
  67. super();
  68. }
  69. /**
  70. * Construct a PresentationML chart from a package part.
  71. *
  72. * @param part the package part holding the chart data,
  73. * the content type must be <code>application/vnd.openxmlformats-officedocument.drawingml.chart+xml</code>
  74. *
  75. * @since POI 3.14-Beta1
  76. */
  77. protected XSLFChart(PackagePart part) throws IOException, XmlException {
  78. super(part);
  79. }
  80. public XSLFTextShape getTitle() {
  81. if (!chart.isSetTitle()) {
  82. chart.addNewTitle();
  83. }
  84. final CTTitle title = chart.getTitle();
  85. if (title.getTx() != null && title.getTx().isSetRich()) {
  86. return new XSLFTextShape(title, null) {
  87. @Override
  88. protected CTTextBody getTextBody(boolean create) {
  89. return title.getTx().getRich();
  90. }
  91. };
  92. } else {
  93. return new XSLFTextShape(title, null) {
  94. @Override
  95. protected CTTextBody getTextBody(boolean create) {
  96. return title.getTxPr();
  97. }
  98. };
  99. }
  100. }
  101. public CellReference setSheetTitle(String title) {
  102. XSSFSheet sheet = getSheet();
  103. sheet.createRow(0).createCell(1).setCellValue(title);
  104. return new CellReference(sheet.getSheetName(), 0, 1, true, true);
  105. }
  106. public String formatRange(CellRangeAddress range) {
  107. return range.formatAsString(getSheet().getSheetName(), true);
  108. }
  109. private XSSFSheet getSheet() {
  110. XSSFSheet sheet = null;
  111. try {
  112. sheet = getWorkbook().getSheetAt(0);
  113. } catch (InvalidFormatException ife) {
  114. } catch (IOException ioe) {
  115. }
  116. return sheet;
  117. }
  118. private PackagePart getWorksheetPart() throws InvalidFormatException {
  119. for (RelationPart part : getRelationParts()) {
  120. if (WORKBOOK_RELATIONSHIP.getRelation().equals(part.getRelationship().getRelationshipType())) {
  121. return getTargetPart(part.getRelationship());
  122. }
  123. }
  124. return null;
  125. }
  126. protected XSSFWorkbook getWorkbook() throws IOException, InvalidFormatException {
  127. if (workbook == null) {
  128. try {
  129. PackagePart worksheetPart = getWorksheetPart();
  130. if (worksheetPart == null) {
  131. workbook = new XSSFWorkbook();
  132. workbook.createSheet();
  133. } else {
  134. workbook = new XSSFWorkbook(worksheetPart.getInputStream());
  135. }
  136. } catch (NotOfficeXmlFileException e) {
  137. workbook = new XSSFWorkbook();
  138. workbook.createSheet();
  139. }
  140. }
  141. return workbook;
  142. }
  143. private XMLSlideShow getSlideShow() {
  144. POIXMLDocumentPart p = getParent();
  145. while(p != null) {
  146. if(p instanceof XMLSlideShow){
  147. return (XMLSlideShow)p;
  148. }
  149. p = p.getParent();
  150. }
  151. throw new IllegalStateException("SlideShow was not found");
  152. }
  153. private PackagePart createWorksheetPart() throws InvalidFormatException {
  154. Integer chartIdx = XSLFRelation.CHART.getFileNameIndex(this);
  155. return getTargetPart(getSlideShow().createWorkbookRelationship(this, chartIdx));
  156. }
  157. protected void saveWorkbook(XSSFWorkbook workbook) throws IOException, InvalidFormatException {
  158. PackagePart worksheetPart = getWorksheetPart();
  159. if (worksheetPart == null) {
  160. worksheetPart = createWorksheetPart();
  161. }
  162. try (OutputStream xlsOut = worksheetPart.getOutputStream()) {
  163. workbook.write(xlsOut);
  164. }
  165. }
  166. private void fillSheet(XSSFSheet sheet, XDDFDataSource<?> categoryData, XDDFNumericalDataSource<?> valuesData) {
  167. int numOfPoints = categoryData.getPointCount();
  168. for (int i = 0; i < numOfPoints; i++) {
  169. XSSFRow row = sheet.createRow(i + 1); // first row is for title
  170. row.createCell(0).setCellValue(categoryData.getPointAt(i).toString());
  171. row.createCell(1).setCellValue(valuesData.getPointAt(i).doubleValue());
  172. }
  173. }
  174. @Override
  175. public void plot(XDDFChartData data) {
  176. super.plot(data);
  177. XSSFSheet sheet = getSheet();
  178. for(XDDFChartData.Series series : data.getSeries()) {
  179. fillSheet(sheet, series.getCategoryData(), series.getValuesData());
  180. }
  181. }
  182. public void importContent(XSLFChart other) {
  183. this.chart.set(other.chart);
  184. }
  185. @Override
  186. protected void commit() throws IOException {
  187. XmlOptions xmlOptions = new XmlOptions(DEFAULT_XML_OPTIONS);
  188. xmlOptions.setSaveSyntheticDocumentElement(new QName(CTChartSpace.type.getName().getNamespaceURI(), "chartSpace", "c"));
  189. if (workbook != null) {
  190. try {
  191. saveWorkbook(workbook);
  192. } catch (InvalidFormatException e) {
  193. throw new POIXMLException(e);
  194. }
  195. }
  196. PackagePart part = getPackagePart();
  197. try (OutputStream out = part.getOutputStream()) {
  198. chartSpace.save(out, xmlOptions);
  199. }
  200. }
  201. }