using System; using System.Collections.Generic; using System.IO; using System.Linq; using ExcelLibrary.SpreadSheet; using MileageTraker.Web.Models; namespace MileageTraker.Web.Utility { public static class ExcelWriter { public static void WriteXls(IEnumerable items, string filename, string worksheetTitle, string worksheetName) { using (var fileStream = new FileStream(filename, FileMode.Create)) WriteXls(items, fileStream, worksheetTitle, worksheetName); } public static byte[] WriteXls(IEnumerable items, string worksheetTitle, string worksheetName) { using (var stream = new MemoryStream()) { WriteXls(items, stream, worksheetTitle, worksheetName); return stream.ToArray(); } } public static void WriteXls(IEnumerable items, Stream stream, string worksheetTitle, string worksheetName) { var workbook = new Workbook(); var worksheet = new Worksheet(worksheetName); // write worksheet header worksheet.Cells[0, 3] = new Cell(worksheetTitle); // write column headers var properties = typeof(T).GetProperties() .Where(p => !p.PropertyType.IsCollection()) .Where(p => !p.Name.Contains("PreviousLog")) .ToList(); properties.Zip( CustomExtensions.GetNumbers(), (p, c) => worksheet.Cells[2, c] = new Cell(p.GetName()) ).ToList(); // write the data items.Zip( CustomExtensions.GetNumbers().Skip(3), (item, r) => properties.Zip(CustomExtensions.GetNumbers(), (p, c) => { var value = p.GetValue(item); string formatString = null; if (value is decimal) // assume that it's currency formatString = "#,##0.00"; if (value is DateTime && p.Name == "Date") formatString = @"YYYY\-MM\-DD"; else if (value is DateTime) formatString = @"YYYY\-MM\-DD hh:mm:ss"; int intValue; // write int-looking values as numbers if (value is string && int.TryParse((string)value, out intValue)) value = intValue; double doubleValue; // write double-looking values as numbers if (value is string && double.TryParse((string)value, out doubleValue)) value = doubleValue; if (value is MileageLogTypeWrapper) value = ((MileageLogTypeWrapper) value).Enum.GetDisplayName(); var cell = formatString != null ? new Cell(value,formatString) : new Cell(value); worksheet.Cells[r, c] = cell; return (string)null; }).ToList()).ToList(); PadWorksheet(worksheet); workbook.Worksheets.Add(worksheet); workbook.Save(stream); } private static void PadWorksheet(Worksheet worksheet) { Func totalCells = () => (worksheet.Cells.LastRowIndex + 1)*(worksheet.Cells.LastColIndex + 1); for (var r = worksheet.Cells.LastRowIndex + 1; totalCells() < 320; r++) { for (var c = 0; c < worksheet.Cells.LastColIndex; c++) { worksheet.Cells[r, c] = new Cell(""); } } } } }