custom header names with SoftArtisans OfficeWriter? - c#

I am using SoftArtisans OfficeWriter tool to create an excel file.
By Using DataImportProperties.UseColumnNames=true the column headers are populated with the class property names but I want to give custom column headers.
Any suggestions?

Donot use DataImportProperties.UseColumnNames=true.Instead use cell specific formatting since it is header so for every cell row/column number is known.ex.
Style headerStyle = wb.CreateStyle();
headerStyle.Font.Size = 10;
headerStyle.Font.Bold = true;
ws.Cells[1, 0].Value = "Name";
ws.Cells[1, 0].ApplyStyle(headerStyle);
You can also merge and group columns as :
ws[0, 0].Value = "Information";
Palette pal = wb.Palette;
Color group1Color = pal.GetClosestColor(255, 244, 205);
headerStyle.BackgroundColor = group1Color;
headerStyle.Font.Bold = true;
ws[0, 0].ApplyStyle(headerStyle);
ws.CreateArea(0, 0, 1, 13).MergeCells();
ws.GroupColumns(0, 12, true);
//True/false keeps the group collapsed/uncollpasedwhen user opens the workbook.

Related

ClosedXML read styles when column and row is overlapping

I want read the styles of this worksheet from Excel via ClosedXML. So on column "E" there is a Fill -> BackgroundColor (blue) and on row "15" there is a Fill -> BackgroundColor (purple). How can I read via ClosedXML which property is now the overlapping one (or which property was set last) so I can set the styles for "E15" correctly?
I was looking for some kind of attribute which indicates that the row "15" was set last and is now the "top layer" but I had no luck so far.
Has someone experienced a similar problem?
string fileName = "d:\\test.xlsx";
using FileStream fs = File.OpenRead(fileName);
using XLWorkbook workbook = new XLWorkbook(fs);
IXLWorksheet worksheet = workbook.Worksheets.Worksheet("Test");
IXLCell cell = worksheet.Cell(5, "E");
Console.WriteLine($"5E value:{cell.Value} color:{cell.Style.Fill.BackgroundColor}");
cell = worksheet.Cell(6, "E");
Console.WriteLine($"6E value:{cell.Value} color:{cell.Style.Fill.BackgroundColor}");
Poperty BackgroundColor contains actual color
screenshot of my test excel
Also you can try to get all styles of worksheet.
((ClosedXML.Excel.XLWorksheet)worksheet).Styles
But XLWorksheet internal class and you get access to it only using reflection and this is not good practice.

How can I partially change the border of a merged cell?

So given this code:
var mergeCells = worksheet.Cells["A1:B5"];
mergeCells.Merge = true;
mergeCells.Style.Border.BorderAround(ExcelBorderStyle.Medium);
var notWorkingCell = worksheet.Cells["C1"];
notWorkingCell.Style.Border.Right.Style = ExcelBorderStyle.Medium;
notWorkingCell.Style.Border.Left.Style = ExcelBorderStyle.None; // <--This does not happen
I would expect that the left border arround notWorkingCell (C1) would be removed. This is not happening:
How can I partially change the border of a merged cell? With pure Excel it is possible.
Looks like the border styles need to be explicitly set on the cell address within the merged cell itself, not the ExcelRange:
var mergeCells = worksheet.Cells["A1:B5"];
mergeCells.Merge = true;
mergeCells.Style.Border.BorderAround(ExcelBorderStyle.Medium);
var notWorkingCell = worksheet.Cells["C1"];
notWorkingCell.Style.Border.Right.Style = ExcelBorderStyle.Medium;
var cellToLeft = notWorkingCell.Start;
worksheet.Cells[cellToLeft.Row, cellToLeft.Column - 1]
.Style.Border.Right.Style = ExcelBorderStyle.None;

Retaining Indentation of the list after adding to PdfCell

I am adding list inside pdfcell.But the identation of this list is not coming properly.
its coming like this:
• One
• Two
• Three
But the same list if add directly to the document,the identation is coming properly.Like below:
• One
• Two
• Three
here is the code :
list = new List(false, 14.4F);
list.ListSymbol = new Chunk("\u2022", FontFactory.GetFont(FontFactory.HELVETICA, 10,iTextSharp.text.Font.BOLD));
ListItem listItem;
listItem = new ListItem(lstrBullets.Trim(), FontFactory.GetFont(FontFactory.HELVETICA, 10, iTextSharp.text.Font.NORMAL));
list.IndentationLeft = lftBulletIndent;
listItem.SetLeading(10.0F, 1.0F);
listItem.Alignment = Element.ALIGN_JUSTIFIED;
list.Add(listItem);
PdfCell cell = new PdfCell();
cell.AddElement(list);
pobjTable.AddCell(cell);
where lftBulletIndent gives the indentation values for list.Please help what i am missing here.How can i retain the indentaion inside a cell?
This how I solved this. I know this is not a proper one.But it worked for me.
I am adding a table with variable width in the first cell of the parent table i.e here pobjTable
PdfPTable DummyTable = new PdfPTable(2);
//Here the floatSpace value changes according to the lftBulletIndent values
float[] headerwidths = { 2f + floatSpace, 98f - floatSpace};
DummyTable.SetWidths(headerwidths);
Pcell = new PdfPCell();
Pcell.Border = Rectangle.NO_BORDER;
DummyTable.AddCell(Pcell);
Pcell = new PdfPCell();
Pcell.AddElement(list);
Pcell.Border = Rectangle.NO_BORDER;
DummyTable.AddCell(Pcell);
pobjTable.AddCell(DummyTable);//Inserting a new table here
pobjTable.AddCell("");

How to set cells' background?

How to set the background of several cells within a row (or of a whole row) in OpenXml?
Having read several articles:
Coloring cells in excel sheet using openXML in C#
Advanced styling in Excel Open XML
I still cannot make it work.
My task is actually at first glance seems to be somewhat easier and a little bit different from what is written in those articles. The mentioned tutorials predominantly show how to create a new document and style it. While I need to change the styling of the existing one.
That is, I have an existing xlsx document (a report template). I populate the report with the necessary values (managed to do it thanks to SO open xml excel read cell value and MSDN Working with sheets (Open XML SDK)). But next I need to mark several rows with, say, red background.
I am neither sure whether to use CellStyle nor if I should use CellFormat or something else...This is what I have got up to now:
SpreadsheetDocument doc = SpreadsheetDocument.Open("ole.xlsx", true);
Sheet sheet = (Sheet)doc.WorkbookPart
.Workbook
.Sheets
.FirstOrDefault();
WorksheetPart worksheetPart = (WorksheetPart)doc.WorkbookPart
.GetPartById(sheet.Id);
Worksheet worksheet = worksheetPart.Worksheet;
CellStyle cs = new CellStyle();
cs.Name = StringValue.FromString("Normal");
cs.FormatId = 0;
cs.BuiltinId = 0;
//where are the style values?
WorkbookStylesPart wbsp = doc.WorkbookPart
.GetPartsOfType<WorkbookStylesPart>()
.FirstOrDefault();
wbsp.Stylesheet.CellStyles.Append(cs);
wbsp.Stylesheet.Save();
Cell cell = GetCell(worksheet, "A", 20);
cell.StyleIndex = 1U;//get the new cellstyle index somehow
doc.Close();
Actually I would greatly appreciate a more light-weight and easy example of how to style, say, cell A20 or range from A20 to J20. Or probably a link to some more consecutive tutorial.
In the end I changed my mind to use cell background and used fonts. Thanks to answer by foson in SO Creating Excel document with OpenXml sdk 2.0 I managed to add a new Font and a new CellFormat, having preserved the original cell's formatting (i.e. having changed the font color only):
SpreadsheetDocument doc = SpreadsheetDocument.Open("1.xlsx", true);
Sheet sheet = (Sheet)doc.WorkbookPart.Workbook.Sheets.FirstOrDefault();
WorksheetPart worksheetPart = (WorksheetPart)doc.WorkbookPart
.GetPartById(sheet.Id);
Worksheet worksheet = worksheetPart.Worksheet;
WorkbookStylesPart styles = doc.WorkbookPart.WorkbookStylesPart;
Stylesheet stylesheet = styles.Stylesheet;
CellFormats cellformats = stylesheet.CellFormats;
Fonts fonts = stylesheet.Fonts;
UInt32 fontIndex = fonts.Count;
UInt32 formatIndex = cellformats.Count;
Cell cell = GetCell(worksheet, "A", 19);
cell.CellValue = new CellValue(DateTime.Now.ToLongTimeString());
cell.DataType = new EnumValue<CellValues>(CellValues.String);
CellFormat f = (CellFormat)cellformats.ElementAt((int)cell.StyleIndex.Value);
var font = (Font)fonts.ElementAt((int)f.FontId.Value);
var newfont = (Font)font.Clone();
newfont.Color = new Color() { Rgb = new HexBinaryValue("ff0000") };
fonts.Append(newfont);
CellFormat newformat = (CellFormat)f.Clone();
newformat.FontId = fontIndex;
cellformats.Append(newformat);
stylesheet.Save();
cell.StyleIndex = formatIndex;
doc.Close();
You have 3 options:
Use MS lib ExcelDataReader which requires your server installing Office and usually does not work if your program is running in IIS.
Use closed source libs.
Use OpenXML.
Try my code using pure OpenXML:
https://stackoverflow.com/a/59806422/6782249
cSimple solution:
Try this: (it works with the nuget package ClosedXML v 0.95.4)
using ClosedXML.Excel;
XLWorkbook wb = new XLWorkbook();
IXLWorksheet ws = wb.Worksheets.Add("Test Background Color");
ws.Cell("A1").Style.Fill.BackgroundColor = XLColor.LightBlue;
ws.Cell("A1").Value = "This cell should have light blue background";
wb.SaveAs(#"c:\Test\test.xlsx");

how to bind DataTable to legend in mschart

I use excel to paint a pic as follow:
please pay attention to the area hightlight in red
my question is:
how to bind the datatable to legend in mschart?
so , except the legend color, also people can see the detail data from the legend.
or, you guys can tell is it feasible to bind in mschart?
Thanks in advance!
As far as I know there is nothing in the API that allows you to simply "bind" your DataTable to a legend.
But you should still be able to manage something like that with some code:
var l = chart1.Legends[0];
l.LegendStyle = LegendStyle.Table;
l.TableStyle = LegendTableStyle.Tall;
l.BorderColor = Color.OrangeRed;
l.Docking = Docking.Bottom;
l.LegendStyle = LegendStyle.Table;
l.HeaderSeparator = LegendSeparatorStyle.DashLine;
l.HeaderSeparatorColor = Color.Red;
var firstColumn = new LegendCellColumn();
l.ColumnType = LegendCellColumnType.SeriesSymbol;
l.CellColumns.Add(firstColumn);
var secondColumn = new LegendCellColumn();
l.ColumnType = LegendCellColumnType.Text;
secondColumn.Text = "#SER";
l.CellColumns.Add(secondColumn);
foreach (DataRow row in dt.Rows)
{
var column = new LegendCellColumn();
column.ColumnType = LegendCellColumnType.Text;
column.HeaderText = row["x"].ToString();
column.Text = "#VALY";
l.CellColumns.Add(column);
}
However, my suggestion would be to include the data in a separate control, rather than as part of the chart itself. It would be much easier to work with if you kept it in one of the .net controls that's meant for tabular data, whether you're in winforms or webforms.

Categories

Resources