Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

EPPlus - LoadFromCollection - Text converted to number

I am writing a program in C# that needs to export a List<MyObject> into Excel and I'm using EPPlus for doing so.

My challenge is that my object has a property:

string Prop1 { get; set; }

And, one of the values I need to export has a value that, for example, is of the form of Prop1 = "123E4".

The challenge is that the EPPlus LoadFromCollection method exports this to Excel, but Excel converts it into a number using scientific notation (Outputted value = 1.23E+06 or 1230000).

I've tried setting the entire column to .Style.Numberformat.Format = "@" (and any other style I could think of) and I've even tried setting the style before and after the LoadFromCollection method is called.

I also tried preceding the string with a ' character, but that actually keeps that character in each cell within that column which then makes the values incorrect for analysis.

I'm playing around with converting my List to a DataTable so as to use the LoadFromDataTable method, but even that seems to not be working.

Any ideas / suggestions on how I can export this as pure text

like image 559
John Bustos Avatar asked Sep 15 '15 13:09

John Bustos


1 Answers

If you have string that look like numbers Excel will warn you with those green trigangles in the corner of the cells. This is assuming you are converting the numbers (if they are numbers) to string using something like .ToString(). There is not way to get around this in Excel but you could turn on the disable warning message for that condition using XML maniulation since EPPlus does not have the ability natively.

Something like this would do it:

public class TestObject
{
    public int Col1 { get; set; }
    public int Col2 { get; set; }
    public string Col3 { get; set; }
}

[TestMethod]
public void Number_String_Test()
{
    //Throw in some data
    var datalist = new List<TestObject>();

    for (var i = 0; i < 10; i++)
    {
        datalist.Add(new TestObject
        {
            Col1 = i,
            Col2 = i *10,
            Col3 = (i*10) + "E4"
        });
    }

    //Create a test file
    var fi = new FileInfo(@"c:\temp\numtest.xlsx");
    if (fi.Exists)
        fi.Delete();

    using (var pck = new ExcelPackage(fi))
    {
        var worksheet = pck.Workbook.Worksheets.Add("Sheet1");
        worksheet.Cells.LoadFromCollection(datalist);

        //This would be the variable drawn from the desired cell range
        var range = "C1:C11";

        //Get reference to the worksheet xml for proper namspace
        var xdoc = worksheet.WorksheetXml;

        //Create the import nodes (note the plural vs singular
        var ignoredErrors = xdoc.CreateNode(XmlNodeType.Element, "ignoredErrors", xdoc.DocumentElement.NamespaceURI);
        var ignoredError = xdoc.CreateNode(XmlNodeType.Element, "ignoredError", xdoc.DocumentElement.NamespaceURI);
        ignoredErrors.AppendChild(ignoredError);

        //Attributes for the INNER node
        var sqrefAtt = xdoc.CreateAttribute("sqref");
        sqrefAtt.Value = range;

        var flagAtt = xdoc.CreateAttribute("numberStoredAsText");
        flagAtt.Value = "1";

        ignoredError.Attributes.Append(sqrefAtt);
        ignoredError.Attributes.Append(flagAtt);

        //Now put the OUTER node into the worksheet xml
        xdoc.LastChild.AppendChild(ignoredErrors);

        pck.Save();
    }
}
like image 200
Ernie S Avatar answered Nov 15 '22 07:11

Ernie S