I am using interop.excel dll and creating an Excel file. I am having issues while writing long numbers as text.
Below is the code I am using. I can use apostrophe, but if you look in formula bar, you can see the cell is formatted.
Is there any other way of writing long numbers to an Excel spreadsheet without seeing the formatted value in the formula bar (using numberformat)?
worksheet.Cells[i, j] = "'" + dr[p];
//var startCell = (Excel.Range)worksheet.Cells[i, j];
//var endCell = (Excel.Range)worksheet.Cells[i, j];
//worksheetRange = worksheet.get_Range(startCell, endCell);
//worksheetRange.NumberFormat = "#####";
If you wanted to do it in one line, you could use the Text function.
Example:
worksheets.Cells[i, j] = "=Text(" + dr[p] + ", \"#\"";
But that probably isn't what you're looking for because this would store the number as a text and display the formula in the formula bar. In that case, like user194076 suggested, you could use .NumberFormat = "#";
or .NumberFormat = "#"; if you don't want it to show in scientific notation.
You can use NumberFormat with '#' or '#'
Example:
Range r= worksheet.Cells;
r.NumberFormat = "#";
Related
I am losing the leading zeros when I copy values from a datatable to an Excel sheet. That's because probably Excel treats the values as a number instead of text.
I am copying the values like so:
myWorksheet.Cells[i + 2, j] = dtCustomers.Rows[i][j - 1].ToString();
How do I format a whole column or each cell as Text?
A related question, how to cast myWorksheet.Cells[i + 2, j] to show a style property in Intellisense?
Below is some code to format columns A and C as text in SpreadsheetGear for .NET which has an API which is similar to Excel - except for the fact that SpreadsheetGear is frequently more strongly typed. It should not be too hard to figure out how to convert this to work with Excel / COM:
IWorkbook workbook = Factory.GetWorkbook();
IRange cells = workbook.Worksheets[0].Cells;
// Format column A as text.
cells["A:A"].NumberFormat = "#";
// Set A2 to text with a leading '0'.
cells["A2"].Value = "01234567890123456789";
// Format column C as text (SpreadsheetGear uses 0 based indexes - Excel uses 1 based indexes).
cells[0, 2].EntireColumn.NumberFormat = "#";
// Set C3 to text with a leading '0'.
cells[2, 2].Value = "01234567890123456789";
workbook.SaveAs(#"c:\tmp\TextFormat.xlsx", FileFormat.OpenXMLWorkbook);
Disclaimer: I own SpreadsheetGear LLC
If you set the cell formatting to Text prior to adding a numeric value with a leading zero, the leading zero is retained without having to skew results by adding an apostrophe. If you try and manually add a leading zero value to a default sheet in Excel and then convert it to text, the leading zero is removed. If you convert the cell to Text first, then add your value, it is fine. Same principle applies when doing it programatically.
// Pull in all the cells of the worksheet
Range cells = xlWorkBook.Worksheets[1].Cells;
// set each cell's format to Text
cells.NumberFormat = "#";
// reset horizontal alignment to the right
cells.HorizontalAlignment = XlHAlign.xlHAlignRight;
// now add values to the worksheet
for (i = 0; i <= dataGridView1.RowCount - 1; i++)
{
for (j = 0; j <= dataGridView1.ColumnCount - 1; j++)
{
DataGridViewCell cell = dataGridView1[j, i];
xlWorkSheet.Cells[i + 1, j + 1] = cell.Value.ToString();
}
}
Solution that worked for me for Excel Interop:
myWorksheet.Columns[j].NumberFormat = "#"; // column as a text
myWorksheet.Cells[i + 2, j].NumberFormat = "#"; // cell as a text
This code should run before putting data to Excel. Column and row numbers are 1-based.
A bit more details. Whereas accepted response with reference for SpreadsheetGear looks almost correct, I had two concerns about it:
I am not using SpreadsheetGear. I was interested in regular Excel
communication thru Excel interop without any 3rdparty libraries,
I was searching for the way to format column by number, not using
ranges like "A:A".
Before your write to Excel need to change the format:
xlApp = New Excel.Application
xlWorkSheet = xlWorkBook.Sheets("Sheet1")
Dim cells As Excel.Range = xlWorkSheet.Cells
'set each cell's format to Text
cells.NumberFormat = "#"
'reset horizontal alignment to the right
cells.HorizontalAlignment = Excel.XlHAlign.xlHAlignRight
I've recently battled with this problem as well, and I've learned two things about the above suggestions.
Setting the numberFormatting to # causes Excel to left-align the value, and read it as if it were text, however, it still truncates the leading zero.
Adding an apostrophe at the beginning results in Excel treating it as text and retains the zero, and then applies the default text format, solving both problems.
The misleading aspect of this is that you now have a different value in the cell. Fortuately, when you copy/paste or export to CSV, the apostrophe is not included.
Conclusion: use the apostrophe, not the numberFormatting in order to retain the leading zeros.
Use your WorkSheet.Columns.NumberFormat, and set it to string "#", here is the sample:
Excel._Worksheet workSheet = (Excel._Worksheet)_Excel.Worksheets.Add();
//set columns format to text format
workSheet.Columns.NumberFormat = "#";
Note: this text format will apply for your hole excel sheet!
If you want a particular column to apply the text format, for example, the first column, you can do this:
workSheet.Columns[0].NumberFormat = "#";
or this will apply the specified range of woorkSheet to text format:
workSheet.get_Range("A1", "D1").NumberFormat = "#";
if (dtCustomers.Columns[j - 1].DataType != typeof(decimal) && dtCustomers.Columns[j - 1].DataType != typeof(int))
{
myWorksheet.Cells[i + 2, j].NumberFormat = "#";
}
I know this question is aged, still, I would like to contribute.
Applying Range.NumberFormat = "#" just partially solve the problem:
Yes, if you place the focus on a cell of the range, you will read text in the format menu
Yes, it align the data to the left
But if you use the type formula to check the type of the value in the cell, it will return 1 meaning number
Applying the apostroph behave better. It sets the format to text, it align data to left and if you check the format of the value in the cell using the type formula, it will return 2 meaning text
//where [1] - column number which you want to make text
ExcelWorksheet.Columns[1].NumberFormat = "#";
//If you want to format a particular column in all sheets in a workbook - use below code. Remove loop for single sheet along with slight changes.
//path were excel file is kept
string ResultsFilePath = #"C:\\Users\\krakhil\\Desktop\\TGUW EXCEL\\TEST";
Excel.Application ExcelApp = new Excel.Application();
Excel.Workbook ExcelWorkbook = ExcelApp.Workbooks.Open(ResultsFilePath);
ExcelApp.Visible = true;
//Looping through all available sheets
foreach (Excel.Worksheet ExcelWorksheet in ExcelWorkbook.Sheets)
{
//Selecting the worksheet where we want to perform action
ExcelWorksheet.Select(Type.Missing);
ExcelWorksheet.Columns[1].NumberFormat = "#";
}
//saving excel file using Interop
ExcelWorkbook.Save();
//closing file and releasing resources
ExcelWorkbook.Close(Type.Missing, Type.Missing, Type.Missing);
Marshal.FinalReleaseComObject(ExcelWorkbook);
ExcelApp.Quit();
Marshal.FinalReleaseComObject(ExcelApp);
You need to format the column to be a string.
You can use the link https://supportcenter.devexpress.com/ticket/details/t679279/import-from-excel-to-gridview
For converting the ExcelDataSource, you can also refer to https://supportcenter.devexpress.com/ticket/details/t468253/how-to-convert-exceldatasource-to-datatable
This is how the formula appears in excel:
I want to use Forecast formula in Excel with EPPLUS from c#. The formula in the code is correct but in Excel appears =#FORECAST(params).
ExcelRange targetDate = sheet.Cells[listItems + 2, 2];
ExcelRange values = sheet.Cells[2, 3, listItems+1, 3];
ExcelRange timeLine = sheet.Cells[2, 2, listItems+1, 2];
sheet.Cells[8, 4].Formula = "=FORECAST.ETS(" + targetDate + "," + values + "," + timeLine + ",1,1)";
sheet.Cells[8, 4].Calculate();
I want to trim the # from the formula in the excel file, like this:
=FORECAST.ETS(B8,C2:C7,B2:B7,1,1)
In code you don't need to put the '=' character
Just use:
sheet.Cells[8, 4].Formula = "FORECAST.ETS(" + targetDate + "," + values + "," + timeLine + ",1,1)";
Similar Problem
I'm having a similar problem with a different formula:
worksheet.Cells[y, x].Formula = "SUMME(C5:C35)";
gave me =#SUMME(C5:C35) within Excel.
Instead of =SUMME(C5:C35).
Solution
It seems that EPPLUS has problems with the German formula. The problem disappears when I use:
worksheet.Cells[y, x].Formula = "SUM(C5:C35)";
My generated Excel now looks like this: =SUMME(C5:C35) (which is what I need)
I know it's not the answer to the exact problem mentioned above. But I thought it might help someone. And maybe serves as a hint to the original question.
I create an Excel file in code. So far, everything works out fine.
Created excel file (image)
I want to create the following chart in code
Excel with Chart (image)
(Notice the selected cells and xseries names)
In Excel its easy.
But how do I do that in code?
My experiment
string values = "='Overall Results'!B3;'Overall Results'!D3;'Overall Results'!F3;'Overall Results'!H3;'Overall Results'!J3";
string xSerie = "='Overall Results'!$B$1:$K$1";
linechart.Series.Add(values, xSerie);
didn't work.
You have to create a string with the EPPlus cell adresses.
string values = worksheet.Cells[3, 2].Address + ":" + worksheet.Cells[3, 4].Address + ":" + worksheet.Cells[3, 6].Address;
linechart.Series.Add(values, ExcelRange.GetAddress(1, 2, 1, 11));
Had this problem aswell, but i found a solution:
For some reason, in order to get multiple specific cells in EPPlus, every cell has to be in a range.
So creating multiple ranges, which each only contains 1 cell, is the way to go
string values = "sheetName!B3:sheetName!B3,sheetName!D3:sheetName!D3,sheetName!F3:sheetName!F3,sheetName!H3:sheetName!H3,sheetName!J3:sheetName!J3";
var valueCells = sheet.Cells[values];
string xSerie = (Same concept);
var xCells = sheet.Cells[xSerie];
linechart.Series.Add(valueCells, xCells);
I am loading data into excel from datatable using LoadFromDataTable method then changed cell format to integer still it is showing error "The number in this cell is formatted as text or preceded by apostrophe".
cell was showing to right side only and number format only on cell property.
still I am not understanding why I am getting this error??.
Dim wsManufacturing As ExcelWorksheet = pck.Workbook.Worksheets.Add("Manufacturing")
wsManufacturing.Cells("A1").LoadFromDataTable(dtManufacturing, True)
Using col As ExcelRange = wsManufacturing.Cells(2, 2, 2 + dtManufacturing.Rows.Count, 2)
col.Style.Numberformat.Format = "#,##0"
col.Style.HorizontalAlignment = ExcelHorizontalAlignment.Right
End Using
You can do like this:
//strValue="98.5%";
double realValue=double.Parse(strValue.Replace("%", string.Empty));
Worksheet.Cells[row + 1, col].Style.Numberformat.Format = "#0\\.00%";
Worksheet.Cells[row + 1, col].Value = realValue;
Changing the format from Text to Number does not change the nature of the entry that was in the cell prior to the format change.
To change entries that were originally textual representations of numbers
Change the cell format to Number
Enter a 1 in some cell
Edit/Copy
Select your cell(s) with the text numbers
Paste Special / Multiply
Delete the original 1
I'm using c# and visual studio to extract data from an excel sheet, put it into an array (adding commas to the end of each string) and then output it to a .CSV file.
Now I've run into a snag that occurs when a cell has either no data, or not the data expected (i.e. an image).
I am assuming that this is on the reading end of the excel sheet, rather than the output to .CSV as when I get this error, I'm not getting any data put into the array.
Here's a snippet of the code that I'm using which has been adapted from a Microsoft example on accessing Excel data using interop.
//Get a range of data.
range = objSheet.get_Range(ranges1, ranges2);
//Retrieve the data from the range.
Object[,] saRet;
saRet = (System.Object[,])range.get_Value(Missing.Value);
//Determine the dimensions of the array.
long iRows;
long iCols;
iRows = saRet.GetUpperBound(0);
iCols = saRet.GetUpperBound(1);
//Build a string that contains the data of the array.
String valueString;
valueString = "Prices";
System.IO.StreamWriter OutWrite = new System.IO.StreamWriter("h:\\out.csv");
for (long rowCounter = 1; rowCounter <= iRows; rowCounter++)
{
for (long colCounter = 1; colCounter <= iCols; colCounter++)
{
//Write the next value into the string.
valueString = String.Concat(valueString,
saRet[rowCounter, colCounter].ToString() + ", ");
}
//Write in a new line.
valueString = String.Concat(valueString, "\n");
}
The error that I recieve is to do with the system.object line is:
Error: Object reference not set to an instance of an object, Line: WindowsFormApplication2
(No I haven't gotten around to renaming my project yet :P )
Cheers, Andy.
This line is dangerous:
valueString = String.Concat(valueString, saRet[rowCounter, colCounter].ToString() + ", ");
...as the result from saRet[rowCounter, colCounter] could be null. If an empty string is acceptable for an empty cell, use Convert.ToString(), which will interpret nulls as empty strings:
valueString = String.Concat(valueString, Convert.ToString(saRet[rowCounter, colCounter]) + ", ");
I suspect this is why you are getting the NullReferenceException.