zoukankan      html  css  js  c++  java
  • [转]比NPOI更討喜的Excel元件-EPPlus

    本文转自:http://blog.darkthread.net/post-2012-05-12-epplus.aspx

    前陣子發表 【潛盾機】將檔案結構匯成Excel文件,從網友佑翔的留言(特此感謝),認識了一顆被我錯過的l好元件 -- EPPlus!

    NPOI源於POI,在很多介面設計上,帶點Java的觀點與風格,雖然能實現各項Excel操作,但函數介面及呼叫步驟,總讓.NET老鳥感覺不順手,就像用筷子吃手扒雞一樣彆扭。例如: 要寫入文字到新的Cell,必須先CreateRow(),再CreateCell(),而不像在Excel VBA透過.Cells(rowIndex, colIndex)一次到位。

    LinqToExcel的出現為讀取Excel提供方便的額外選擇,能用熟悉的LINQ語法查詢Excel內容是件暢快的事,只可惜LinqToExcel只限於讀取,要產生Excel,還是得回歸NPOI。

    EPPlus是一個起始於2009年底的Open Source專案,目標鎖定在伺服器端產生Office Open XML Excel檔(Excel 2007/2010的xlsx,不包含Excel 2003 xls),提供比NPOI更直覺、更簡便的API介面! 用.Cells[rowIndex, colIndex]就能直接存取欄位,甚至用.Cells[r1, c1, r2, c2]就能取得一段選取範圍,再一口氣改變它們的樣式;而要指定字型顏色時,使用Cells[…].Style.Font.Color.SetColor(Color.Red)就能搞定,不像NPOI需要CreateFont(), CreateCellStyle(), SetFont(), SetCellStyle()一長串操作。這才是.NET客心中理想的好元件呀~~

    不過我不禁好奇,為何先前很少聽人提起,幾無知名度。私自揣摩,猜想可能與EPPlus只支援xlsx,無法相容於Excel 2003的xls格式,在需顧及不特定使用群時會有Excel版本門檻的考量。(雖然微軟提供免費的Excel檢視工具,但需要額外安裝仍會有部署面的考量) 另一方面,這個元件採用LGPL授權,代表如果要包含在產品中散佈,產品也必須Open Source(非100%要Open Source,授權限制可參見下方newbie的留言),也會造成一些軟體廠商採用上的疑慮。再者,微軟本身提供Open XML SDK,已涵蓋Excel檔的操作,有些開發者已直接採用SDK,沒想到再花時間評估更便捷元件(呼應了我在前篇文章的感嘆,有小錦囊後真的會讓人錯過其他更犀利的選擇),也可能是原因之一。

    依我的看法,隨著時光飛逝,舊版Excel相容的重要性會逐年下降,而應用於網站時,只要不是販售網站程式本體,倒不必擔憂LGPL的限制(可參照先前的討論)。至於與Open XML SDK相比,初看語法,EPPlus確實如網友所說,具有"只見新人笑,不見舊人哭"的魅力! 真的可以跟NPOI說Bye Bye囉,在直覺易用上也已把Open XML SDK比下去。總評之後,EPPlus應是可以安心採用的解決方案。

    好東西當然要也要實測體驗一下威力,就同樣用上回的檔案結構匯出Excel案例吧! 這回改用EPPlus來處理寫成Excel的部分。

    要在專案中引用EPPlus,最快的方法一樣是透過NuGet: (還不會用NuGet的人,有沒有覺得自己已經輸在起跑點上?)

    參考Zeeshan Umar的文章,三兩下就改好程式:

    排版顯示純文字
        //加入擴充方法: SetQuickStyle,指定前景色/背景色/水平對齊
        private static void SetQuickStyle(this ExcelRange range,
            Color foreColor,
            Color bgColor = default(Color),
            ExcelHorizontalAlignment hAlign = ExcelHorizontalAlignment.Left)
        {
            range.Style.Font.Color.SetColor(foreColor);
            if (bgColor != default(Color))
            {
                range.Style.Fill.PatternType = ExcelFillStyle.Solid;
                range.Style.Fill.BackgroundColor.SetColor(bgColor);
            }
            range.Style.HorizontalAlignment = hAlign;
        }
     
        /// <summary>
        /// 將目錄下的目錄檔案結構匯出成Excel工作表
        /// </summary>
        /// <param name="dirPath">要匯出的目錄路徑</param>
        /// <param name="excelPath">匯出Excel路徑</param>
        /// <param name="filter">過濾函數,傳入Path進行判斷,傳回true時表排除</param>
        /// <returns></returns>
        public static void WebTreeToExcel(
            string dirPath, string excelPath,
            Func<string, bool> filter = null)
        {
            //將目錄結構整理成清單
            List<WebItem> list = new List<WebItem>();
            explore(list, dirPath, 0);
            //建立Excel
            using (ExcelPackage p = new ExcelPackage())
            {
                ExcelWorksheet sheet = p.Workbook.Worksheets.Add("Site Tree");
                int colIdx = 1;
                foreach (string colName in "Path;File;Description".Split(';'))
                {
                    sheet.Cells[1, colIdx++].Value = colName;
                }
                //修改標題列Style
                sheet.Cells[1, 1, 1, 3].SetQuickStyle(Color.Yellow, Color.Green,
                        ExcelHorizontalAlignment.Center);
     
                int rowIdx = 2;
                foreach (var item in list)
                {
                    //若bypass檢測傳回true,則略過該筆
                    if (filter != null && filter(item.Path))
                        continue;
                    //將Path放在第一欄(稍後隱藏)
                    sheet.Cells[rowIdx, 1].Value = item.Path;
                    //存入檔名或目錄名
                    sheet.Cells[rowIdx, 2].Value = 
                        new String(' ', item.Layer * 4) + item.Name;
                    if (item.IsFolder)
                    {
                        sheet.Cells[rowIdx, 2].SetQuickStyle(Color.Blue);
                    }
                    rowIdx++;
                }
                //第一欄隱藏
                sheet.Column(1).Hidden = true;
                //自動伸縮欄寬
                sheet.Column(2).AutoFit();
              sheet.Column(2).Width += 2;
              sheet.Column(3).Width = 50;
                //寫入檔案
                p.SaveAs(new FileInfo(excelPath));
            }

    一模一樣的結果,跟上回的NPOI寫法相比,是不是清爽順眼很多呢? 在以xlsx為主的網站應用場合,大家就大膽用下去吧!

  • 相关阅读:
    第三章 AOP
    第二章 IoC
    第一章 Spring 概述
    框架整合
    后台管理工程搭建
    技术架构
    淘淘商城简介
    电商行业背景
    前言
    FutureTask的使用
  • 原文地址:https://www.cnblogs.com/freeliver54/p/5072874.html
Copyright © 2011-2022 走看看