How to get LineBreaks in a single Cell in EPPlus with RichText - c#

I use the following Code:
using (var package = new ExcelPackage()) {
var worksheet = package.Workbook.Worksheets.Add("Test");
var cell = worksheet.Cells[1, 1];
var r1 = cell.RichText.Add("TextLine1" + "\r\n");
r1.Bold = true;
var r2 = cell.RichText.Add("TextLine2" + "\r\n");
r2.Bold = false;
package.SaveAs(...);
}
But in the Excel file the newLines are gone...
I tried also with "\n" and "\r" but nothing was working...

Finally I found the solution. Here is a working sample:
using (var package = new ExcelPackage(fileInfo)) {
var worksheet = package.Workbook.Worksheets.Add("Test");
var cell = worksheet.Cells[1, 1];
cell.Style.WrapText = true;
cell.Style.VerticalAlignment = ExcelVerticalAlignment.Top;
var r1 = cell.RichText.Add("TextLine1" + "\r\n");
r1.Bold = true;
var r2 = cell.RichText.Add("TextLine2" + "\r\n");
r2.Bold = false;
package.Save();
}
But I think I found a bug in the Lib: This Code is NOT working:
using (var package = new ExcelPackage(fileInfo)) {
var worksheet = package.Workbook.Worksheets.Add("Test");
var cell = worksheet.Cells[1, 1];
cell.Style.WrapText = true;
cell.Style.VerticalAlignment = ExcelVerticalAlignment.Top;
var r1 = cell.RichText.Add("TextLine1" + "\r\n");
r1.Bold = true;
var r2 = cell.RichText.Add("TextLine2" + "\r\n");
r2.Bold = false;
cell = worksheet.Cells[1, 1];
var r4 = cell.RichText.Add("TextLine3" + "\r\n");
r4.Bold = true;
package.Save();
}
When I get the same range again and add new RichText Tokens, the old LineBreaks are deleted... (They are actually converted to "\n" and this is not working in Excel.)

The Encoding of new line in excel cell is 10.
I think you have to do someihing like thise:
var r1 = cell.RichText.Add("TextLine1" + ((char)10).ToString());

using (var package = new ExcelPackage(fileInfo)) {
var worksheet = package.Workbook.Worksheets.Add("Test");
var cell = worksheet.Cells[1, 1];
cell.Style.WrapText = true;
cell.Style.VerticalAlignment = ExcelVerticalAlignment.Top;
var r1 = cell.RichText.Add("TextLine1" + "\n\n");
r1.Bold = true;
var r2 = cell.RichText.Add("TextLine2" + "\n\n");
r2.Bold = false;
package.Save();
}

Related

Need to convert scientific value to text

I am trying to convert csv to xls in which there is Bank Account No (16 digit) need to convert it to text
I tried with EPPlus package by which xls is getting generated easily but Bank Account column gets converted to scientific value.Also tried to convert column to numeric and text but thats not working
private void csvToXls(string source,string destination,string fileName)
{
string csvFileName = source;
string excelFileName = destination+"/"+fileName+".xls";
string worksheetsName = "sheet 1";
bool firstRowIsHeader = false;
var format = new ExcelTextFormat();
format.Delimiter = '|';
format.EOL = "\n"; // DEFAULT IS "\r\n";
// format.TextQualifier = '"';
using (ExcelPackage package = new ExcelPackage(new FileInfo(excelFileName)))
{
ExcelWorksheet worksheet = package.Workbook.Worksheets.Add(worksheetsName);
worksheet.Cells["A1"].LoadFromText(new FileInfo(csvFileName), format, OfficeOpenXml.Table.TableStyles.None, firstRowIsHeader);
foreach (var cell in worksheet.Cells["C:C"])
{
cell.Value = Convert.ToString(cell.Value);
}
foreach (var cell in worksheet.Cells["AC:AC"])
{
cell.Value = Convert.ToString(cell.Value);
}
worksheet.Cells["C:C"].Style.Numberformat.Format = "#0";
worksheet.Cells["C:C"].Style.Numberformat.Format = "#";
worksheet.Cells["AC:AC"].Style.Numberformat.Format = "#";
package.Save();
}
}
Need to convert columns to text which should not be scientific value.Please suggest
Input : In test.csv below input is there
IMDATA||12345678910124567895274|1|NAME|||||||||TEST|||||||||||TESTING||||3301003726558|TDATASTING|TESTING|27-09-2019
Getting Output :
Expected Output :
You need to provide eDataTypes to LoadFromText method for each column, if no types provide for the column it will set to the General by default
So, provide the `eDataTypes to ExcelTextFormat.
I just added for 3 columns and its worked well.
public static void csvToXls(string source, string destination, string fileName)
{
string csvFileName = source;
string excelFileName = destination + "/" + fileName + ".xls";
string worksheetsName = "sheet 1";
bool firstRowIsHeader = false;
var format = new ExcelTextFormat();
var edataTypes = new eDataTypes[] { eDataTypes.String, eDataTypes.String, eDataTypes.String };
format.DataTypes = edataTypes;
format.Delimiter = '|';
format.EOL = "\n"; // DEFAULT IS "\r\n";
// format.TextQualifier = '"';
using (ExcelPackage package = new ExcelPackage(new FileInfo(excelFileName)))
{
ExcelWorksheet worksheet = package.Workbook.Worksheets.Add(worksheetsName);
worksheet.Cells["A1"].LoadFromText(new FileInfo(csvFileName), format, OfficeOpenXml.Table.TableStyles.None, firstRowIsHeader);
package.Save();
}
}
OR
You can try to read the text manually
public static void csvToXls(string source, string destination, string fileName)
{
string csvFileName = source;
string excelFileName = destination + "/" + fileName + ".xls";
string worksheetsName = "sheet 1";
using (ExcelPackage package = new ExcelPackage(new FileInfo(excelFileName)))
{
ExcelWorksheet worksheet = package.Workbook.Worksheets.Add(worksheetsName);
var text = File.ReadAllText(source);
var rows = text.Split('\n');
for (int rowIndex = 0; rowIndex < rows.Length; rowIndex++)
{
var excelRow = worksheet.Row(rowIndex+1);
var columns = rows[rowIndex].Split('|');
for (int colIndex = 0; colIndex < columns.Length; colIndex++)
{
worksheet.Cells[rowIndex +1, colIndex +1].Value = columns[colIndex];
}
}
package.Save();
}
}

c# Merged cells as header address epplus

How do I set HeaderAddress to two cells of a clustered bar chart in EPPlus? I have the below data from my database output, where first column is as you can see merged cells.
I am looking for the following layout of the data
Please take note that the images are from a replica of the data, but generated inside Excel.
What I've tried so far is basically
ExcelChartSerie s = chart.Series.Add(axis.Address, xAxis.Address);
s.HeaderAddress = new ExcelAddress(startRow + r, GetColumnNumberByName(startColumn), startRow + 1, GetColumnNumberByName(startColumn) + 1);
where I more or less select the current row and two columns. This gives me "Address must be a row, column or single cell", but in order to get this to work, I must select multiple cells, no?
Epplus does not have the ability to set it. it is not so difficult but it requires XML manipulation. Kind of ugly but it gets the job done. Not knowing your code I made up a quick unit test that demos. It has to match to the right chart type so if it is not BarClustered let me know:
[TestMethod]
public void Chart_Meged_Header_Test()
{
//Throw in some data
var datatable = new DataTable("tblData");
datatable.Columns.AddRange(new[]
{
new DataColumn("Col1", typeof (string)),
new DataColumn("Col2", typeof (int))
});
for (var i = 0; i < 10; i++)
{
var row = datatable.NewRow();
row[0] = $"item {(i%2 == 0 ? "A" : "B")}";
row[1] = i * 10;
datatable.Rows.Add(row);
}
//Create a test file
var fileInfo = new FileInfo(#"c:\temp\Chart_Meged_Header_Test.xlsx");
if (fileInfo.Exists)
fileInfo.Delete();
using (var pck = new ExcelPackage(fileInfo))
{
var workbook = pck.Workbook;
var worksheet = workbook.Worksheets.Add("Sheet1");
worksheet.Cells["B1"].LoadFromDataTable(datatable, true);
worksheet.Column(4).Style.Numberformat.Format = "m/d/yyyy";
var chart = worksheet.Drawings.AddChart("chart test", eChartType.BarClustered);
var serie = chart.Series.Add(worksheet.Cells["C2:C11"], worksheet.Cells["B2:B11"]);
chart.SetPosition(0, 0, 3, 0);
chart.SetSize(120);
//Add merged headers
worksheet.Cells["A2"].Value = "Group 1";
worksheet.Cells["A2:A6"].Merge = true;
worksheet.Cells["A7"].Value = "Group 2";
worksheet.Cells["A7:A11"].Merge = true;
//Get reference to the worksheet xml for proper namespace
var chartXml = chart.ChartXml;
var nsm = new XmlNamespaceManager(chartXml.NameTable);
var nsuri = chartXml.DocumentElement.NamespaceURI;
nsm.AddNamespace("c", nsuri);
//Get the Series ref and its cat
var serNode = chartXml.SelectSingleNode("c:chartSpace/c:chart/c:plotArea/c:barChart/c:ser", nsm);
var catNode = serNode.SelectSingleNode("c:cat", nsm);
//Get Y axis reference to replace with multi level node
var numRefNode = catNode.SelectSingleNode("c:numRef", nsm);
var multiLvlStrRefNode = chartXml.CreateNode(XmlNodeType.Element, "c:multiLvlStrRef", nsuri);
//Set the proper cell reference and replace the node
var fNode = chartXml.CreateElement("c:f", nsuri);
fNode.InnerXml = numRefNode.SelectSingleNode("c:f", nsm).InnerXml;
fNode.InnerXml = fNode.InnerXml.Replace("$B$2", "$A$2");
multiLvlStrRefNode.AppendChild(fNode);
catNode.ReplaceChild(multiLvlStrRefNode, numRefNode);
//Set the multi level flag
var noMultiLvlLblNode = chartXml.CreateElement("c:noMultiLvlLbl", nsuri);
var att = chartXml.CreateAttribute("val");
att.Value = "0";
noMultiLvlLblNode.Attributes.Append(att);
var catAxNode = chartXml.SelectSingleNode("c:chartSpace/c:chart/c:plotArea/c:catAx", nsm);
catAxNode.AppendChild(noMultiLvlLblNode);
pck.Save();
}
}
Gives this as the output:

How to pull List View items into Excel?

I have been stuck on this issue for a a day or so and need some help. In my application, I have some data in a listview, which is
public void OnHostPing(HostPinger host)
{
if (InvokeRequired)
{
Invoke(new OnPingDelegate(OnHostPing), new object[] { host });
return;
}
lock (_table)
{
ListViewItem item = (ListViewItem)_table[host.ID];
if (item != null)
{
item.SubItems[0].Text = host.HostIP.ToString();
item.SubItems[1].Text = host.HostName;
item.SubItems[2].Text = host.HostDescription;
item.SubItems[3].Text = host.StatusName;
item.SubItems[4].Text = host.SentPackets.ToString();
item.SubItems[5].Text = host.ReceivedPackets.ToString();
item.SubItems[6].Text = PercentToString(host.ReceivedPacketsPercent);
item.SubItems[7].Text = host.LostPackets.ToString();
item.SubItems[8].Text = PercentToString(host.LostPacketsPercent);
item.SubItems[9].Text = host.LastPacketLost ? "Yes" : "No";
item.SubItems[10].Text = host.ConsecutivePacketsLost.ToString();
item.SubItems[11].Text = host.MaxConsecutivePacketsLost.ToString();
item.SubItems[12].Text = host.RecentlyReceivedPackets.ToString();
item.SubItems[13].Text = PercentToString(host.RecentlyReceivedPacketsPercent);
item.SubItems[14].Text = host.RecentlyLostPackets.ToString();
item.SubItems[15].Text = PercentToString(host.RecentlyLostPacketsPercent);
item.SubItems[16].Text = host.CurrentResponseTime.ToString();
item.SubItems[17].Text = host.AverageResponseTime.ToString("F");
item.SubItems[18].Text = host.MinResponseTime.ToString();
item.SubItems[19].Text = host.MaxResponseTime.ToString();
item.SubItems[20].Text = DurationToString(host.CurrentStatusDuration);
item.SubItems[21].Text = DurationToString(host.GetStatusDuration(HostStatus.Alive));
item.SubItems[22].Text = DurationToString(host.GetStatusDuration(HostStatus.Dead));
item.SubItems[23].Text = DurationToString(host.GetStatusDuration(HostStatus.DnsError));
item.SubItems[24].Text = DurationToString(host.GetStatusDuration(HostStatus.Unknown));
item.SubItems[25].Text = PercentToString(host.HostAvailability);
item.SubItems[26].Text = DurationToString(host.TotalTestDuration);
item.SubItems[27].Text = DurationToString(host.CurrentTestDuration);
}
else
{
item = new ListViewItem(new string[]
{
host.HostIP.ToString(), host.HostName, host.HostDescription,
host.StatusName,
host.SentPackets.ToString(),
host.ReceivedPackets.ToString(), PercentToString(host.ReceivedPacketsPercent),
host.LostPackets.ToString(), PercentToString(host.LostPacketsPercent),
host.LastPacketLost ? "Yes" : "No",
host.ConsecutivePacketsLost.ToString(), host.MaxConsecutivePacketsLost.ToString(),
host.RecentlyReceivedPackets.ToString(), PercentToString(host.RecentlyReceivedPacketsPercent),
host.RecentlyLostPackets.ToString(), PercentToString(host.RecentlyLostPacketsPercent),
host.CurrentResponseTime.ToString(), host.AverageResponseTime.ToString("F"),
host.MinResponseTime.ToString(), host.MaxResponseTime.ToString(),
DurationToString(host.CurrentStatusDuration),
DurationToString(host.GetStatusDuration(HostStatus.Alive)),
DurationToString(host.GetStatusDuration(HostStatus.Dead)),
DurationToString(host.GetStatusDuration(HostStatus.DnsError)),
DurationToString(host.GetStatusDuration(HostStatus.Unknown)),
PercentToString(host.HostAvailability),
DurationToString(host.TotalTestDuration),
DurationToString(host.CurrentTestDuration)
});
What I can't seem to figure out is, how to get that data exported to Excel? I am able to export static data to Excel with this code
public static string RunSample1(DirectoryInfo outputDir)
{
if (!outputDir.Exists) throw new Exception("outputDir does not exist!");
FileInfo newFile = new FileInfo(outputDir.FullName + #"\sample1.xlsx");
if (newFile.Exists)
{
newFile.Delete(); // ensures we create a new workbook
newFile = new FileInfo(outputDir.FullName + #"\sample1.xlsx");
}
using (ExcelPackage package = new ExcelPackage(newFile))
{
// add a new worksheet to the empty workbook
ExcelWorksheet worksheet = package.Workbook.Worksheets.Add("Current Devices");
//Add the headers
//worksheet.Cells[1, 1].Value = "ID";
worksheet.Cells[1, 1].Value = "";
worksheet.Cells[1, 2].Value = "Product";
worksheet.Cells[1, 3].Value = "Quantity";
worksheet.Cells[1, 4].Value = "Price";
worksheet.Cells[1, 5].Value = "Value";
//Add some items...
worksheet.Cells["A2"].Value = 12001;
worksheet.Cells["B2"].Value = "Nails";
worksheet.Cells["C2"].Value = 37;
worksheet.Cells["D2"].Value = 3.99;
What I can't figure out is how to get those listview items in to the spreadsheet cells instead of static data. ListViewItems doesn't seem to yield the properties I would expect. Can someone help me out a bit here?
I found a solution using Microsoft.Office.Interop.Excel instead of trying to use the EPPlus solution.

Exporting to Excel rich text box

In c#, Rich text content are saved to database in below format
< b>Hello< /b>.
I need to export this to MS Excel sheet as Hello (with bold letters)
When ever i try to export the content in excel , its not showing in rich text. Kindly help me . Thanks,
var workbook = new HSSFWorkbook();
var sheet = workbook.CreateSheet("");
int rowNumber = 1;
NPOI.SS.UserModel.IFont font = workbook.CreateFont();
font.Boldweight = (short)(NPOI.SS.UserModel.FontBoldWeight.BOLD);
font.FontHeight = 210;
font.FontName = "Calibri";
NPOI.SS.UserModel.ICellStyle headerCell = workbook.CreateCellStyle();
headerCell.FillBackgroundColor = NPOI.SS.UserModel.IndexedColors.GREY_25_PERCENT.Index;
headerCell.FillForegroundColor = NPOI.SS.UserModel.IndexedColors.GREY_25_PERCENT.Index;
headerCell.FillPattern = NPOI.SS.UserModel.FillPatternType.SOLID_FOREGROUND;
headerCell.VerticalAlignment = NPOI.SS.UserModel.VerticalAlignment.CENTER;
headerCell.WrapText = true;
headerCell.SetFont(font);
headerCell.BorderBottom = NPOI.SS.UserModel.BorderStyle.THIN;
headerCell.BorderLeft = NPOI.SS.UserModel.BorderStyle.THIN;
headerCell.BorderRight = NPOI.SS.UserModel.BorderStyle.THIN;
headerCell.BorderTop = NPOI.SS.UserModel.BorderStyle.THIN;
NPOI.SS.UserModel.IFont fontShort = workbook.CreateFont();
fontShort.Boldweight = (short)(NPOI.SS.UserModel.FontBoldWeight.NORMAL);
fontShort.FontName = "Calibri";
NPOI.SS.UserModel.ICellStyle normalCell = workbook.CreateCellStyle();
normalCell.FillBackgroundColor = 50;
normalCell.VerticalAlignment = NPOI.SS.UserModel.VerticalAlignment.CENTER;
normalCell.WrapText = true;
normalCell.SetFont(fontShort);
normalCell.BorderBottom = NPOI.SS.UserModel.BorderStyle.THIN;
normalCell.BorderLeft = NPOI.SS.UserModel.BorderStyle.THIN;
normalCell.BorderRight = NPOI.SS.UserModel.BorderStyle.THIN;
normalCell.BorderTop = NPOI.SS.UserModel.BorderStyle.THIN;
NPOI.SS.UserModel.ICellStyle emptyCell = workbook.CreateCellStyle();
emptyCell.SetFont(font);
emptyCell.BorderBottom = NPOI.SS.UserModel.BorderStyle.NONE;
emptyCell.BorderLeft = NPOI.SS.UserModel.BorderStyle.NONE;
emptyCell.BorderRight = NPOI.SS.UserModel.BorderStyle.NONE;
emptyCell.BorderTop = NPOI.SS.UserModel.BorderStyle.NONE;
var headerRow = sheet.CreateRow(0);
var output ="<b>HelloWorld</b>"
var row = sheet.CreateRow(rowNumber++);
row.CreateCell(0).SetCellValue(output);
row.Cells[0].CellStyle = normalCell;

EPPlus with HTML input

I have one Data table which is converting to the excel.for this i am using EPPlus dll. Here i am getting the generated excel file. but my problem is there are 2 columns are existing with rich text value. After Conversion the above column is always showing data with HTML tag. How I resolve this issue. Please help me. thanks in advance
My code is shown below
try
{
using (SPSite site = new SPSite(SPContext.Current.Web.Url))
{
using (SPWeb web = site.OpenWeb())
{
DataTable dtTemp = new DataTable();
if (ViewState["DTSource"] != null)
dtTemp = (DataTable)ViewState["DTSource"];
using (ExcelPackage pck = new ExcelPackage())
{
//Create the worksheet
ExcelWorksheet ws = pck.Workbook.Worksheets.Add("Sheet1");
//Load the datatable into the sheet, starting from cell A1. Print the column names on row 1
if (dtTemp != null && dtTemp.Rows.Count > 0)
{
ws.Cells["A1"].LoadFromDataTable(dtTemp, true);
using (ExcelRange rng = ws.Cells["A1:" + GetColumnName(dtTemp.Columns.Count) + "1"])
{
rng.Style.Font.Bold = true;
rng.Style.Fill.PatternType = ExcelFillStyle.Solid;
rng.Style.Fill.BackgroundColor.SetColor(Color.FromArgb(79, 129, 189));
rng.Style.Font.Color.SetColor(Color.White);
}
for (int i = 0; i < dtTemp.Columns.Count; i++)
{
if (dtTemp.Columns[i].DataType.FullName.Contains("DateTime"))
{
ws.Cells[2, i + 1, dtTemp.Rows.Count + 1, i + 1].Style.Numberformat.Format = "MM/dd/yyyy";
ws.Column(i + 1).Width = 15;
}
using (ExcelRange col = ws.Cells[2, 1, 2 + dtTemp.Rows.Count, 1])
{
col.Style.Numberformat.Format = "#,##0.00";
col.Style.HorizontalAlignment = ExcelHorizontalAlignment.Center;
}
using (ExcelRange col = ws.Cells[2, 4, 2 + dtTemp.Rows.Count, 4])
{
col.IsRichText = true;
col.Style.HorizontalAlignment = ExcelHorizontalAlignment.Left;
}
Page.Response.Clear();
Page.Response.AddHeader("content-disposition", "attachment; filename=ExceptionTracker_" + DateTime.Now.ToString("yyyyMMddHHmmss") + ".xlsx");
Page.Response.ContentType = "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet";
Page.Response.BinaryWrite(pck.GetAsByteArray());
Page.Response.End();
}
}
else
{
string script = "window.frameElement.cancelPopUp(); return false;";
Page.ClientScript.RegisterClientScriptBlock(this.GetType(), "Close Window", script, true);
}
}
}
}
}
catch (Exception ex)
{
throw ex;
}
Shouldn't this part be somewhere else? Maybe after you have finished creating the file?
Page.Response.Clear();
Page.Response.AddHeader("content-disposition", "attachment; filename=ExceptionTracker_" + DateTime.Now.ToString("yyyyMMddHHmmss") + ".xlsx");
Page.Response.ContentType = "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet";
Page.Response.BinaryWrite(pck.GetAsByteArray());
Page.Response.End();

Categories