トップ 差分 一覧 ソース 検索 ヘルプ PDF RSS ログイン

Visual Studio .NET 2003 C#、Excel COM 操作

[カテゴリ:言語]
[カテゴリ:C#]
[カテゴリ:Excel]

=================================
※このページを見る前に。
今のところ、C#からのExcel操作は以下がベストと思ってます。(2007/10/23)
[Visual Studio .NET 2003 C#、Excel2000 COM 操作クラス]
=================================

ExcelCOM操作(2007/01/13)

参照指定方法

プロジェクト→参照の追加→COMタブ→
Microsoft Excel 9.0 Object Livraly 1.3
X:\Program Files\Microsoft Office\Office\EXCEL9.OLB

参考:ExcelCOMの使い方

Microsoft.Office.Interop.Excel 名前空間
http://msdn2.microsoft.com/ja-jp/library/microsoft.office.interop.excel(VS.80).aspx

.NET 開発者の観点から捉えた Excel オブジェクト モデル
http://www.microsoft.com/japan/msdn/office/vsto2003/ExcelObj.aspx

Visual C# を使用した Office アプリケーションのプログラミング:
http://www.microsoft.com/japan/msdn/office/vsto2003/OffCSharp.aspx

C#, VB.NET で Excel が終了しない:
http://blogs.wankuma.com/jeanne/archive/2005/12/20/20102.aspx

COM オブジェクトを解放する
http://jeanne.wankuma.com/tips/programing/02-releasecom.html

Excel関係のフレーム
http://www.bcap.co.jp/hanafusa/dotnet/Excelflm.htm

.NET 開発者の観点から捉えた Excel オブジェクト モデル
http://www.microsoft.com/japan/msdn/officedev/vsto2003/ExcelObj.asp#excelobj_link14

Word や Excel などの Office 製品の制御:
http://www.microsoft.com/japan/msdn/vbasic/migration/tips/office.aspx

はてな C#でExcelのファイルを操作するプログラムを書いてください。1.c:¥wb1.xls というファイルを開く2.そのファイルのA列にデータが入っている数を・・
http://www.hatena.ne.jp/1102171960

ReleaseComObject C# excel
http://www.google.co.jp/search?hl=ja&q=ReleaseComObject+C%23+excel&btnG=Google+%E6%A4%9C%E7%B4%A2&lr=lang_ja

C# mschart
http://www.google.co.jp/search?sourceid=navclient-ff&ie=UTF-8&rlz=1B2GGGL_jaJP176&q=C%23+mschart

.NETからExcelの基本的な操作方法(起動・終了) − VBレスキュー(花ちゃん) VB.NET .NET Tips サンプル
http://www.bcap.co.jp/hanafusa/dotnet/Excel01.htm

Word や Excel などの Office 製品の制御
http://www.microsoft.com/japan/msdn/vbasic/migration/tips/office.aspx

参考:Excel.Rangeの指定方法

Range C# - Google 検索(http://www.google.co.jp/search?sourceid=navclient&hl=ja&ie=UTF-8&rls=GGLD,GGLD:2004-19,GGLD:ja&q=Range+C%23

参考:指定セルへ画像貼り付け

マクロの編集(http://www2s.biglobe.ne.jp/~iryo/2vba/vba29e.html

参考:Selectionで選択されているオブジェクトの種類を確認する。(20080129)

[Visual Studio .NET 2003 C#、COMオブジェクトの種類を得る。]

C#からVBS経由でExcel操作(2007/01/13)

概要

C#からExcelを使うと開放忘れでリークしやすい。
VBS(or JScript)を使えば自動で開放してくれる。
ということで、以下を行う仕組みを作る。

    +------------------------+
    |最低限必要なExcelCOM準備|
    |VBSスクリプトを起動     |
C#  +-----------+-----------+
↑              ↓
================↓=====================
↓              ↓
VBS  +----------+----------+
     |       Excel操作      |
     +----------------------+

単に、C#からVBSを1アプリとして起動するイメージではなく、
関数レベルでI/Fできる。
つまり、C#からVBSユーザ関数をパラメータ付きでCallしたり、
VBSユーザ関数からの戻り値をC#側で受けたりできる。

サンプルソース

参照設定に以下を追加
「Microsoft Script Control 1.0」
「Microsoft Excel 9.0 Object Library 1.3」

using System;
using System.Collections;
using MSScriptControl;
using System.Threading;
using System.Runtime.InteropServices;
using System.Windows.Forms;

namespace WindowsApplication1
{
    /// <summary>
    /// ClassExcelTest の概要の説明です。
    /// </summary>
    public class ClassExcelTest
    {
        public ClassExcelTest()
        {
            // 
            // TODO: コンストラクタ ロジックをここに追加してください。
            //
        }

        public static void run()
        {
            string msg = "";

            //
            // ExcelCOMを操作する前後のプロセスをチェックすることで
            // COMの開放漏れがわかる。
            //

            msg = excel_process_check();
            MessageBox.Show("実行前のExcelプロセス \r\n" + msg);

            run_sub();
            Thread.Sleep(2000);

            msg = excel_process_check();
            MessageBox.Show("実行後のExcelプロセス \r\n" + msg);

        }

        public static void run_sub()
        {
            //
            ArrayList rcws = new ArrayList();
            ScriptControl scl = new ScriptControl();
            try 
            {
                rcws.Add(scl);
                Excel.Application excel = new Excel.Application();
                rcws.Add(excel);

                int sampleno = 2;
                switch (sampleno) 
                {
                    case 1:
                        //
                        // ExecuteStatement() サンプル
                        //
                        scl.Language = "VBScript";
                        scl.AddObject("objExcel", excel, false);
                        scl.ExecuteStatement("objExcel.Visible = True");
                        scl.ExecuteStatement("Set objWorkBook = objExcel.WorkBooks.Add");
                        scl.ExecuteStatement("objExcel.ActiveCell.Value = \"hoge\"");
                        scl.ExecuteStatement("Set objRange = Range(\"A1\")");
                        Thread.Sleep(2000);
                        scl.Eval("objRange");
                        scl.ExecuteStatement("objWorkBook.Saved = True");
                        scl.ExecuteStatement("objWorkBook.Close");
                        scl.ExecuteStatement("objExcel.UserControl = False");
                        break;
                    case 2:
                        //
                        // AddCode()、Run() サンプル
                        //
                        scl.Language = "VBScript";
                        string code = "";
                        // VBSユーザ関数にパラメータ渡したり
                        code += "Function BookAdd(objExcel)" + "\r\n";
                        code += "  objExcel.Visible = True" + "\r\n";
                        code += "  objExcel.UserControl = False" + "\r\n";
                        code += "  Set BookAdd = objExcel.WorkBooks.Add" + "\r\n";
                        code += "End Function" + "\r\n";
                        // VBSユーザ関数からパラメータ受け取ったり
                        code += "Function cell_get(objBook)" + "\r\n";
                        code += "  objBook.ActiveCell.Value = \"hoge\"" + "\r\n";
                        code += "  Set cell_get = objBook.Range(\"A1\")" + "\r\n";
                        code += "End Function" + "\r\n";
                        //
                        code += "Function BookClose(objBook)" + "\r\n";
                        code += "  objBook.Saved = True" + "\r\n";
                        code += "  objBook.Close" + "\r\n";
                        code += "End Function" + "\r\n";
                        //
                        scl.AddCode(code);
                        Excel.Workbook objBook = null;
                        rcws.Add(objBook);
                        try 
                        {
                            //
                            // VSBユーザ関数へのパラメータは
                            // object の配列で渡す。
                            // object[] parameters = new Object[0]; // パラメータ無しのとき
                            //
                            object[] parameters = {excel};
                            objBook = (Excel.Workbook)scl.Run("BookAdd",ref parameters);
                        }
                        catch (Exception e)
                        {
                            throw e;
                        }
                        try
                        {
                            //
                            // VBSユーザ関数からのreturnを受けるときは
                            // objectで受けて、asで識別してキャストする。
                            //
                            object[] parameters = {excel};
                            object ret = null;
                            ret = scl.Run("cell_get",ref parameters);
                            if ((ret as Excel.Rectangle) != null)
                            {
                                MessageBox.Show("Rectangle");
                            }
                            if ((ret as Excel.Range) != null)
                            {
                                Excel.Range objRange = ret as Excel.Range;
                                Thread.Sleep(2000);
                                MessageBox.Show("Range.Value:" + objRange.Value);
                                rcws.Add(ret);
                                rcws.Add(objRange);
                            }
                        }
                        catch (Exception e)
                        {
                            throw e;
                        }
                        try 
                        {
                            // object[] parameters = new Object[0];
                            object[] parameters = {objBook};
                            scl.Run("BookClose",ref parameters);
                        }
                        catch (Exception e)
                        {
                            throw e;
                        }
                        break;
                }
                excel.Quit();
            }
            catch(Exception e)
            {
                MSScriptControl.Error err = scl.Error;
                if (err == null) 
                {
                    MessageBox.Show(e.ToString());
                } 
                else 
                {
                    string msg = "ScriptControl.Error \r\n";
                    msg += string.Format("number:{0} desc:{1} \r\n", err.Number, err.Description);
                    msg += string.Format("line:{0} column:{1} \r\n", err.Line, err.Column);
                    msg += string.Format("source:{0}", err.Source);
                    MessageBox.Show(e.ToString() + "\r\n" + msg);
                }
            }
            finally 
            {
                //
                // COMを開放してやる。
                // これをしないとExcelのプロセスがタスクマネージャ上に残る。
                //
                foreach (object obj in rcws)
                {
                    if (obj != null && Marshal.IsComObject(obj))
                    {
                        Marshal.ReleaseComObject(obj);
                    }
                }
                GC.Collect();    // 一応
            }

        }

        //
        // Excelのプロセスを取得
        // IDとウィンドウタイトルから素性を判断できる。
        //
        public static string excel_process_check()
        {
            System.Diagnostics.Process[] ps =
                System.Diagnostics.Process.GetProcessesByName("Excel");

            string msg = "";
            foreach (System.Diagnostics.Process p in ps)
            {
                msg += string.Format("Id:{0} Title:{1} \r\n", p.Id, p.MainWindowTitle);
            }
            return msg;
        }
    }
}

最終更新時間:2008年01月29日 13時02分53秒