JCom(Java-COMブリッジ)



FAQ(よくある質問)


LinuxなどWindows以外でも動きますか?

いいえ、動きません。
JComはJNI(Java Native Interface)を使っており、Windows以外には対応していません。
そもそも、COM自体がWindows以外では動きません。 イメージ図



以下のエラーが出て、JComが実行できません

Exception in thread "main" java.lang.UnsatisfiedLinkError: no jcom in java.library.path
        at java.lang.ClassLoader.loadLibrary(Unknown Source)
        at java.lang.Runtime.loadLibrary0(Unknown Source)
        at java.lang.System.loadLibrary(Unknown Source)
        at jp.ne.so_net.ga2.no_ji.jcom.IDispatch.(IDispatch.java:288)
jcom.dll のロードに失敗していますね。 どうやら、JComのインストールに失敗していると思われます。 以下のプログラムを実行して、使われているJavaのパスを確認してください。(ShowPath.java)

public class ShowPath {
    public static void main(String[] args) throws Exception {
        System.out.println("java.home="+System.getProperty("java.home"));
        System.out.println("この下の bin     に jcom.dll を、");
        System.out.println("この下の lib/ext に jcom.jar をコピーしましょう。");
    }
}
でも、私も完全には理解していないのですが、 コンパイル時には、OSの環境変数の CLASSPATH を参照し、 実行時には、Javaのプロパティの、"java.home"を参照しているようです。 例えばWindowsの場合、C:\JDK1.3\ がコンパイル時、実行時には C:\Program Files\JavaSoft\JRE\1.3\ という感じになるようです。

サーブレットでも使えますか?

使えます。
読者からサーブレットでも使えたという報告がありました。 ただし、サーブレットのあるサーバはOSがWindowsである必要があります。

アプレットでも使えますか?

まず無理でしょう。 JComはCOMとアクセスするため、JNI(Java Native Interface)を使っていますが、 アプレットではこのJNIは使えません。 まず使えるようにするには、独自のセキュリティを設定し、 クライアントにExcelなど利用するCOMのアプリケーションがインストールされている必要があります。 さらにJComがダウンロード済みでなければなりません。 可能かもしれませんが、障害が多く、オススメできません。

ISink、コネクションポイント、イベントには対応していますか?

ゴメンなさい。対応していません。

Java の Long に対応していますか? 4バイト以上の整数を扱いたいのですが。

COM自体が64bit整数をサポートしていません。従って、JComで対応することは出来ません。 以下の方法で回避できるでしょう。
  • 上位4バイトと下位4バイトに分ける
  • 文字列に直して送る。

    不思議なことに、COMにはVT_I8 という、それらしい定義があるにもかかわらず、 実際にはVT_I8にはほとんど対応していません。

    エラーが出ているのですが、HRESULTとは何ですか?

    COM(もしくはWindows)のエラーコードです。 VC++を持っている方なら、winerror.hでその意味を調べることが出来ます。 ある程度、原因を特定することが出来るでしょう。

    Excelのシートやセルのコピーが使いたいのですが・・・

    Version2.22以前のjcom.dllにバグがありました。申し訳ありません。
    引数にオブジェクト、すなわちIDispatchがある場合にエラーになってしまいます。 (判断の順序により、IDispatchがすべてIUnknownと誤認されてました。) また、引数にnullを設定した場合もエラーになってしまいます。 (VT_NULLにすべきをVT_EMPTYにしていました)
    これらのバグはVersion2.23で修正しましたので、それを使ってください。 あわせて、ExcelRange.Copy()、ExcelWorksheet.Copy()、そして ExcelWorksheets.Copy()の メソッドを実装しました。

    JBuilderから使えますか?

    使えます。
    JBuilderを使った場合、あらかじめ以下のディレクトリにコピーしてください。
    (JBuilder)/jdk1.3/jre/bin/          jcom.dll
    (JBuilder)/jdk1.3/jre/lib/ext/      jcom.jar
    (JBuilder)/jdk1.3/lib/ext/          jcom.jar
    

    メニューで[ツール / JDKの設定]を選びます。
    JDK設定ダイアログが開きます。ユーザホームの下の[java 1.3.0-C]を選びます。
    右にクラスの一覧がありますが、この中にjcomを追加します。
    追加ボタンを押し、(JBuilder)/jdk1.3/jre/lib/ext/jcom.jarを指定します。
    これでJComを使うことができます。
    上記はJBuilder4Foundationで確認しました。

    引数に配列を使えますか?

    できません。配列には対応していません。
    独自のCOMを作っている場合は、引数の数を増やすか、getCount()/getAt(int index);のような インターフェースにして回避してください。

    Excelの罫線や固定枠など、サポートされていない機能を使いたいのですが

    ExcelApplicationなどのラッパクラスでサポートされていない機能を使う場合は、 IDispatchなどの低レベルインターフェースを使って、直接COMを扱うことになります。 これら2つは混ぜて使うことができます。 ですから、サポートしている機能についてはラッパクラスを使い、 サポートしていない箇所については低レベルインターフェースを使えばよいでしょう。
    以下のプログラムを参考にしてください。
    TextExcelBorder.java

    基本的にはJavaからほとんどすべての操作ができるわけですが、 すべての操作をJavaからやるのはあまりオススメできません。 なるべく、定型フォーマットを用意し、それに対して必要箇所に 値を入れるような、そんな「軽い」使い方をお薦めします。 例えば、フォーマットを変更する際は、「軽く」作っていた方が 楽ですし、開発も早いハズです。

    マルチスレッドに対応していますか?

    ごめんなさい。対応していません。
    サンプルプログラム samples/testExcelSvr.java の31行目、 THREAD_NUMを1以外にすると対応できていないのが確認できます。 つまり、エラーになります。
    static final int THREAD_NUM = 1; // なぜか1以外では希にエラーが起こる。原因不明

    help me !

    Excelのマクロを実行させるには?

    VBでこんな感じなら、
        mySum = Application.Run("MYCUSTOM.XLM!My_Func_Sum", 1, 5)
        MsgBox "マクロの結果: " & mySum
    これをJComで書くと、こんな感じになるでしょう。(多分)
           Object[] runArg = new Object[3];
           runArg[0] = "MYCUSTOM.XLM!My_Func_Sum";
           runArg[1] = new Integer(1);
           runArg[2] = new Integer(5); 
           Object mySum = xlApp.Method("Run", runArg);
           System.out.println("マクロの結果:"+mySum.toString());
    
    また、マクロの実行だけなら、JComを使わずに以下の方法で行う方法もあります。 そちらもご検討ください。
    	Process proc = runtime.exec( "start C:\\test\\sample.xls /e");

    C++ファイルを英語圏の環境でコンパイルできますか?

    一部のコンパイラ(英語版のVisual C++など)では、日本語のコメントが混じったソースファイルを正しくコンパイルできません。 その場合は日本語のコメントを削除する必要があります。 手作業で行う方法と、native2asciiなどのツールを使う方法が考えられるでしょう。 日本語と英語以外の言語については不明です。

    ところでJComって邪道じゃないですか?

    はい、邪道です。
    ですから、JComの利用はなるべく回避するよう設計すべきだと思います。 私がプロジェクトリーダーの場合でも、なるべく使わないようにするでしょう。 しかし、システムがJavaへ移行していても、クライアントはWindows、ドキュメントはOfficeが まだまだ主流です。 邪道と分かっていても、通らざるを得ない場合もあるのです。 そしてJComは他のどんな道よりも、近道なのです。

    ExcelのラッパクラスにはC++のソースのコメントがありますが、あれはどうやって作ったのですか?

    以下の手順で作成しました。
    VisualC++6.0とOffice97の環境です。
  • クラスライブラリを立ち上げます。
  • 「メッセージマップ」タブで「クラスの追加ボタン」を押し、「クラスライブラリから」を選びます。
  • オフィスのディレクトリのExcel8.olbを選びます。
  • 「クラスの確認」ダイアログがでるので、出力したいクラスを選びます。複数選択できますが、1クラス=1ファイルがよいでしょう。ヘッダファイル、インプリメントファイルに適当なファイル名を入れ、OKボタンを押します。
  • ファイルが出力されます。
    VCを熟知した人ならば、それを参考にすれば、独自のラッパクラスを作ることができるでしょう。

    J-COMというケーブルインターネットの会社がありますが、関係があるのですか?

    ありません。(ジュピターテレコムJ-COM Broadband)
    いや、JComの名前を付けるときに、実はJ-COMは知っていたのです。 しかし当時はケーブルTVだけで、コンピュータ業界とは縁遠いものだと思ってました。 それと、ローカルな企業と勘違いしていて、全国的に有名とは思っていませんでした。 すいません>J-COM(ジュピターテレコム)さん。
    私は普段から、ソフトに名前を付けるなら、誰が見ても想像できる名前にしようと思っていました。 JDBCなんて、誰が見てもJavaのODBCです。 とても分かりやすいです。 ならば、JavaでCOMやDCOMを扱うモノはJCOM以外にありえません。 それ以外の名前は思いつきませんでした。 そして、JComと名づけ、リリースしたのです。 ところがその後、インターネットが流行り、JCOMさんもケーブルTVだけではなく、 ケーブルインターネット市場に進出し、ますますご清栄とのこと。 しかも、地方の会社ではなく、業界No1だったし。 私の住んでいるところもサービスエリアなので、ちゃっかり入会してお世話になっています。

    Visual-C++以外のコンパイラでコンパイルしたいのですが

    DLLを作成するためのC++のソースはVisual-C++用に書かれています。 COMに関するライブラリや日本語文字コードのライブラリは Visual-C++付属のものを使っているので、他のコンパイラでは うまくいかないと思います。 その場合、手持ちのコンパイラ用に書き換える必要がでてきますが、 COMやJNIなどの知識が必要なので、それに詳しくなければお薦めできません。

    ただ単に、JComを利用したいだけなら、C++のコンパイラは必要ありません。 必要なのはJavaだけで、jcom.dllをそのまま使うだけです。
    戻る