Browse Source

Merge pull request #1556 from gas162/master

#1338 Added Copy Charts to Sheet.CopyTo
pull/1570/head
Tony Q. 2 months ago
committed by GitHub
parent
commit
9bf4164ca3
No known key found for this signature in database GPG Key ID: B5690EEEBB952194
  1. 2
      main/HPSF/Section.cs
  2. 2
      ooxml/XSSF/Streaming/SXSSFRow.cs
  3. 2
      ooxml/XSSF/Streaming/SXSSFSheet.cs
  4. 5
      ooxml/XSSF/UserModel/XSSFRelation.cs
  5. 95
      ooxml/XSSF/UserModel/XSSFSheet.cs
  6. 2
      openxml4Net/Util/ZipInputStreamZipEntrySource.cs
  7. 14
      testcases/ooxml/XSSF/SXSSFITestDataProvider.cs
  8. 65
      testcases/ooxml/XSSF/UserModel/TestXSSFSheetColumns.cs
  9. 26
      testcases/ooxml/XSSF/UserModel/TestXSSFSheetCopyTo.cs

2
main/HPSF/Section.cs

@ -76,7 +76,7 @@ namespace NPOI.HPSF
/// <summary>
/// This section's properties.
/// </summary>
private IDictionary<long, Property> properties = new SortedDictionary<long, Property>();
private SortedDictionary<long, Property> properties = new SortedDictionary<long, Property>();
/// <summary>
/// This member is <c>true</c> if the last call to {@link

2
ooxml/XSSF/Streaming/SXSSFRow.cs

@ -26,7 +26,7 @@ namespace NPOI.XSSF.Streaming
public class SXSSFRow : IRow, IComparable<SXSSFRow>
{
private readonly SXSSFSheet _sheet; // parent sheet
private readonly IDictionary<int, SXSSFCell> _cells = new Dictionary<int, SXSSFCell>();
private readonly Dictionary<int, SXSSFCell> _cells = new Dictionary<int, SXSSFCell>();
private short _style = -1; // index of cell style in style table
private bool _zHeight; // row zero-height (this is somehow different than being hidden)
private float _height = -1;

2
ooxml/XSSF/Streaming/SXSSFSheet.cs

@ -37,7 +37,7 @@ namespace NPOI.XSSF.Streaming
internal XSSFSheet _sh;
private readonly SXSSFWorkbook _workbook;
//private TreeMap<Integer, SXSSFRow> _rows = new TreeMap<Integer, SXSSFRow>();
private readonly IDictionary<int, SXSSFRow> _rows = new Dictionary<int, SXSSFRow>();
private readonly Dictionary<int, SXSSFRow> _rows = new Dictionary<int, SXSSFRow>();
private readonly SheetDataWriter _writer;
private int _randomAccessWindowSize = SXSSFWorkbook.DEFAULT_WINDOW_SIZE;
private readonly Lazy<AutoSizeColumnTracker> _autoSizeColumnTracker;

5
ooxml/XSSF/UserModel/XSSFRelation.cs

@ -376,10 +376,7 @@ namespace NPOI.XSSF.UserModel
/// <param name="relation">Relation to remove</param>
public static void RemoveRelation(XSSFRelation relation)
{
if (_table.ContainsKey(relation.Relation))
{
_table.Remove(relation.Relation);
}
_table.Remove(relation.Relation);
}
/// <summary>

95
ooxml/XSSF/UserModel/XSSFSheet.cs

@ -34,11 +34,13 @@ using System.Collections;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Text;
using Cysharp.Text;
using System.Xml;
using CT_Shape = NPOI.OpenXmlFormats.Vml.CT_Shape;
using ST_EditAs = NPOI.OpenXmlFormats.Dml.Spreadsheet.ST_EditAs;
using System.Xml.Linq;
using System.Diagnostics;
namespace NPOI.XSSF.UserModel
{
@ -4254,6 +4256,95 @@ namespace NPOI.XSSF.UserModel
}
CopySheetImages(dest as XSSFWorkbook, newSheet);
CopyCharts(newSheet);
}
private void CopyCharts(XSSFSheet newSheet)
{
XSSFDrawing sheetDrawing = GetDrawingPatriarch();
if(sheetDrawing == null)
return;
var anchors = sheetDrawing.GetCTDrawing().CellAnchors.Where(x=>x is CT_TwoCellAnchor).Cast<CT_TwoCellAnchor>();
var chartAnchors = anchors.Where(x => x.graphicFrame?.graphic?.graphicData?.uri == XSSFRelation.NS_CHART);
var newSheetDrawing = newSheet.CreateDrawingPatriarch();
var sourceCharts = sheetDrawing.GetCharts();
foreach(var cellAnchor in chartAnchors)
{
XSSFClientAnchor newAnchor = new XSSFClientAnchor(
(int) cellAnchor.from.colOff,
(int) cellAnchor.from.rowOff,
(int) cellAnchor.to.colOff,
(int) cellAnchor.to.rowOff,
cellAnchor.from.col,
cellAnchor.from.row,
cellAnchor.to.col,
cellAnchor.to.row);
if(cellAnchor.editAsSpecified)
{
switch(cellAnchor.editAs)
{
case ST_EditAs.twoCell:
newAnchor.AnchorType = AnchorType.MoveAndResize;
break;
case ST_EditAs.oneCell:
newAnchor.AnchorType = AnchorType.MoveDontResize;
break;
case ST_EditAs.absolute:
case ST_EditAs.NONE:
default:
newAnchor.AnchorType = AnchorType.DontMoveAndResize;
break;
}
}
var data = cellAnchor.graphicFrame.graphic.graphicData.Any?.FirstOrDefault() ?? null;
if(string.IsNullOrEmpty(data))
continue;
string id = null;
try
{
var elem = XElement.Parse(data);
id = elem.Attributes().FirstOrDefault(x => x.Name.LocalName == "id").Value;
}
catch
{
Debug.WriteLine("Warning: Can't get id for chart.");
continue;
}
var newXSSFChart = newSheetDrawing.CreateChart(newAnchor) as XSSFChart;
var linkedChart = sourceCharts.FirstOrDefault(x=>x.GetPackageRelationship().Id == id);
if(linkedChart == null)
continue;
var newXSSFChartAxis = newXSSFChart.GetAxis();
foreach(var axis in linkedChart.GetAxis())
{
newXSSFChartAxis.Add(axis);
}
var linkedCTChart = linkedChart.GetCTChart();
var newCTChart = newXSSFChart.GetCTChart();
newCTChart.plotArea = linkedCTChart.plotArea;
newCTChart.extLst = linkedCTChart.extLst;
newCTChart.title = linkedCTChart.title;
newCTChart.legend = linkedCTChart.legend;
newCTChart.autoTitleDeleted = linkedCTChart.autoTitleDeleted;
newCTChart.view3D = linkedCTChart.view3D;
newCTChart.backWall = linkedCTChart.backWall;
newCTChart.sideWall = linkedCTChart.sideWall;
newCTChart.dispBlanksAs = linkedCTChart.dispBlanksAs;
newCTChart.plotVisOnly = linkedCTChart.plotVisOnly;
newCTChart.floor = linkedCTChart.floor;
newCTChart.pivotFmts = linkedCTChart.pivotFmts;
newCTChart.showDLblsOverMax = linkedCTChart.showDLblsOverMax;
}
}
public XSSFWorkbook GetWorkbook()
@ -6441,7 +6532,7 @@ namespace NPOI.XSSF.UserModel
}
}
lblforbreak:
lblforbreak:
int EMUwidth = Units.PixelToEMU((int) Math.Round(width_px, 1));
if(x >= EMUwidth)
{

2
openxml4Net/Util/ZipInputStreamZipEntrySource.cs

@ -30,6 +30,8 @@ namespace NPOI.OpenXml4Net.Util
zipEntries = new List<FakeZipEntry>();
bool going = true;
if(inp.Position != 0)
inp.Position = 0;
while (going)
{
ZipEntry zipEntry = inp.GetNextEntry();

14
testcases/ooxml/XSSF/SXSSFITestDataProvider.cs

@ -65,19 +65,21 @@ namespace NPOI.XSSF
throw new ArgumentException("Expected an instance of XSSFWorkbook or SXSSFWorkbook");
}
XSSFWorkbook result;
try
{
MemoryStream baos = new MemoryStream(8192);
wb.Write(baos, false);
Stream is1 = new MemoryStream(baos.ToArray());
result = new XSSFWorkbook(is1);
using(MemoryStream baos = new MemoryStream(8192))
{
wb.Write(baos, false);
using(Stream is1 = new MemoryStream(baos.ToArray()))
{
return new XSSFWorkbook(is1);
}
}
}
catch (IOException e)
{
throw new Exception(e.Message, e);
}
return result;
}
public IWorkbook CreateWorkbook()

65
testcases/ooxml/XSSF/UserModel/TestXSSFSheetColumns.cs

@ -217,49 +217,52 @@ namespace TestCases.XSSF.UserModel
[Test]
public void RemoveColumn_RemoveExistingColumn_ColumnIsRemoved()
{
XSSFWorkbook wb = new XSSFWorkbook();
XSSFSheet sheet = (XSSFSheet)wb.CreateSheet("sheet1");
_ = sheet.CreateColumn(1);
_ = sheet.CreateColumn(2);
_ = sheet.CreateColumn(3);
FileInfo file;
using(XSSFWorkbook wb = new XSSFWorkbook())
{
XSSFSheet sheet = (XSSFSheet)wb.CreateSheet("sheet1");
ClassicAssert.NotNull(sheet.GetColumn(1));
ClassicAssert.NotNull(sheet.GetColumn(2));
ClassicAssert.NotNull(sheet.GetColumn(3));
ClassicAssert.AreEqual(1, sheet.FirstColumnNum);
ClassicAssert.AreEqual(3, sheet.LastColumnNum);
_ = sheet.CreateColumn(1);
_ = sheet.CreateColumn(2);
_ = sheet.CreateColumn(3);
sheet.RemoveColumn(sheet.GetColumn(3));
ClassicAssert.NotNull(sheet.GetColumn(1));
ClassicAssert.NotNull(sheet.GetColumn(2));
ClassicAssert.NotNull(sheet.GetColumn(3));
ClassicAssert.AreEqual(1, sheet.FirstColumnNum);
ClassicAssert.AreEqual(3, sheet.LastColumnNum);
ClassicAssert.IsNull(sheet.GetColumn(3));
ClassicAssert.AreEqual(1, sheet.FirstColumnNum);
ClassicAssert.AreEqual(2, sheet.LastColumnNum);
sheet.RemoveColumn(sheet.GetColumn(3));
_ = sheet.CreateColumn(3);
ClassicAssert.IsNull(sheet.GetColumn(3));
ClassicAssert.AreEqual(1, sheet.FirstColumnNum);
ClassicAssert.AreEqual(2, sheet.LastColumnNum);
sheet.RemoveColumn(sheet.GetColumn(1));
_ = sheet.CreateColumn(3);
ClassicAssert.IsNull(sheet.GetColumn(1));
ClassicAssert.AreEqual(2, sheet.FirstColumnNum);
ClassicAssert.AreEqual(3, sheet.LastColumnNum);
sheet.RemoveColumn(sheet.GetColumn(1));
_ = sheet.CreateColumn(1);
ClassicAssert.IsNull(sheet.GetColumn(1));
ClassicAssert.AreEqual(2, sheet.FirstColumnNum);
ClassicAssert.AreEqual(3, sheet.LastColumnNum);
ClassicAssert.NotNull(sheet.GetColumn(3));
ClassicAssert.AreEqual(3, sheet.LastColumnNum);
_ = sheet.CreateColumn(1);
sheet.RemoveColumn(sheet.GetColumn(2));
ClassicAssert.NotNull(sheet.GetColumn(3));
ClassicAssert.AreEqual(3, sheet.LastColumnNum);
ClassicAssert.IsNull(sheet.GetColumn(2));
ClassicAssert.AreEqual(1, sheet.FirstColumnNum);
ClassicAssert.AreEqual(3, sheet.LastColumnNum);
sheet.RemoveColumn(sheet.GetColumn(2));
FileInfo file = TempFile.CreateTempFile("poi-", ".xlsx");
Stream output = File.OpenWrite(file.FullName);
wb.Write(output);
output.Close();
ClassicAssert.IsNull(sheet.GetColumn(2));
ClassicAssert.AreEqual(1, sheet.FirstColumnNum);
ClassicAssert.AreEqual(3, sheet.LastColumnNum);
file = TempFile.CreateTempFile("poi-", ".xlsx");
using(Stream output = File.OpenWrite(file.FullName))
{
wb.Write(output);
}
}
XSSFWorkbook wbLoaded = new XSSFWorkbook(file.ToString());
XSSFSheet sheetLoaded = (XSSFSheet)wbLoaded.GetSheet("sheet1");

26
testcases/ooxml/XSSF/UserModel/TestXSSFSheetCopyTo.cs

@ -17,11 +17,12 @@
using NPOI.SS.UserModel;
using NPOI.SS.Util;
using NPOI.XSSF;
using NPOI.XSSF.UserModel;
using NUnit.Framework;using NUnit.Framework.Legacy;
using NUnit.Framework;
using NUnit.Framework.Legacy;
using System;
using System.Linq;
using TestCases.SS.UserModel;
namespace TestCases.XSSF.UserModel
{
@ -88,5 +89,26 @@ namespace TestCases.XSSF.UserModel
destSheet.MergedRegions
.Select(r => r.FormatAsString())));
}
[Test]
public void CopySheetToWorkbookShouldCopyCharts()
{
XSSFWorkbook sourceWorkbook = XSSFTestDataSamples.OpenSampleWorkbook("WithThreeCharts.xlsx");
XSSFSheet srcDataSheet = (XSSFSheet)sourceWorkbook.GetSheetAt(0);
XSSFWorkbook destWorkbook = new XSSFWorkbook();
srcDataSheet.CopyTo(destWorkbook, srcDataSheet.SheetName, true, true);
XSSFSheet srcChartSheet = (XSSFSheet)sourceWorkbook.GetSheetAt(1);
srcChartSheet.CopyTo(destWorkbook, srcChartSheet.SheetName, true, true);
var destSheet = destWorkbook.GetSheetAt(1);
ClassicAssert.NotNull(destSheet);
ClassicAssert.AreEqual(2, (srcChartSheet.CreateDrawingPatriarch() as XSSFDrawing).GetCharts().Count);
ClassicAssert.AreEqual(2, (destSheet.CreateDrawingPatriarch() as XSSFDrawing).GetCharts().Count);
ClassicAssert.AreEqual(2, (destSheet.CreateDrawingPatriarch() as XSSFDrawing).GetCharts()[0].GetAxis().Count);
}
}
}
Loading…
Cancel
Save