Delphi Programming / Object Pascal

[掲載 2013年12月28日] [更新 2013年12月28日] エクセル操作フォームEx |
エクセル操作フォームEx 参考コード類
複数のブックの表示とブック間の操作 |
| 動作確認等 |
Windows 7 U64(SP1) + Delphi XE Pro + Excel 2010 |
| 別のエクセル操作フォームEx を実行時に生成して表示 |
エクセル操作フォームEx を使用したアプリケーションを複数起動して、各々に別のブックを表示すれば当然、複数のブックを開くことになります。
ここでは、エクセル操作フォームEx を起動して、そこからボタンクリック等で別のエクセル操作フォームEx を生成して起動します。新たに生成したエクセル操作フォームEx で別のブックを表示すれば複数のブックを開くことになります。ただし、エクセルのインスタンスを生成すると、それは別のプロセスとして生成されます。
また、エクセル操作フォームEx の仕様上、後で起動したエクセル操作フォームEx が、前面に表示されてしまい、起動元のエクセル操作フォームEx をクリックしても前面に移動できません。現在のところ回避策はありません。 |
[備考]
たとえ同じエクセルでも、別のプロセスで起動しているアプリケーションは、プロセスを越えての操作はできません。特殊な手順、方法が必要です。文字列 (テキスト) だけは特別で、専用のメッセージ類があります。 |
 |
図1
別のエクセル操作フォームEx 起動 |
リスト1
別のエクセル操作フォームEx を実行時に生成して表示 |
procedure TplExcelFormEx1.Button1Click(Sender: TObject);
var
objExcelSheet : OleVariant;
ExcelForm : TplExcelFormEx;
begin
//現在のブックの1番目のシートのオブジェクト
objExcelSheet := xlfExcelBook.Worksheets[1];
//エクセル操作フォームExを生成
ExcelForm := TplExcelFormEx.Create(Self);
ExcelForm.xlfBookFullPath := ExpandFileName('../Book2.xls');
//グリッドライン等を表示
ExcelForm.xlfDisplayGridLines := True;
ExcelForm.xlfDisplayWorkBookTabs := True;
ExcelForm.xlfDisplayHeadings := True;
ExcelForm.PanelRight.Visible := False;
//表示してセルに値を代入
ExcelForm.Show;
ExcelForm.xlfCellValue['A3'] := 'ABC';
ExcelForm.xlfBookSaved := True;
//次のような、プロセスを超えた操作はできない
try
objExcelSheet.Copy(Before := ExcelForm.xlfExcelBook.Worksheets[1]);
except
end;
end;
| 現在のエクセル操作フォームEx に別のブックを表示 |
エクセル操作フォームEx で指定のブックを表示して、そこに別のブックを表示します。
複数のブックを開くことになります。このサンプルでは、最初に開いたブックのシートを、後から開いたブックのシートに挿入します。このように複数のブックを開いておくと、シートの挿入だけではなく、ブック間の操作が可能となります。
エクセル操作フォームEx は後から開いたブックを閉じる操作は行いません。プログラマの責任で実装することになります。 |
 |
図2
最初のブックを表示 |
 |
図3
2 番目のブックを表示 |
 |
図4
2 番目のブックにシートを挿入
|
リスト2
現在のエクセル操作フォームEx に別のブックを表示 |
procedure TplExcelFormEx1.Button2Click(Sender: TObject);
var
objExcelSheet : OleVariant;
objExcelApp : OleVariant;
objExcelBook : OleVariant;
begin
//現在のブックの1番目のシートのオブジェクト
objExcelSheet := xlfExcelBook.Worksheets[1];
//新しく別のブックを開く
//このブックがアクティブになる
objExcelApp := xlfExcelApp.Application;
objExcelBook := objExcelApp.Workbooks.Open(ExpandFileName('../Book2'));
objExcelBook.WorkSheets[1].Cells[3, 2].Value := 320;
//指定時間後に、最初のブックの1番目のシートを新しいブックの1番目のシートの前に挿入
Sleep(3000);
objExcelSheet.copy(Before := objExcelBook.WorkSheets[1]);
//指定時間後に保存しないで閉じる
Sleep(3000);
objExcelBook.Close(SaveChanges := False);
end;
| エクセル操作フォームEx を使用しないで複数のブックを開いて操作 |
次のコードは、エクセル操作フォームEx を使用しないで複数のブックを開いて操作する例です。ここでは、CreateOleObject でエクセルのオブジェクトを生成しています。
上のサンプルと同じく、最初に開いたブックのシートを、後で開いたブックのシートに挿入します。このようにシートの挿入だけではなく、ブック間の操作が可能となります。
エクセル操作フォームEx は、エクセルを表示して操作を実行することを目的としていますが、エクセル操作フォームEx を使用しない方法では、ブックを表示しなくても操作が可能です。 |
[備考]
昔のエクセルでは、ブックを別のウィンドウで開いたり、同じウィンドウに重ねて表示するかを設定可能なバージョンもありました。現在は、少なくとも Excel 2007, Excel 2010 では、同じウィンドウに重ねて表示する仕様となっています。別のウィンドウでブックを開くようにするには、レジストリの操作が必要です。 |
 |
図5
最初のブックを表示 |
 |
図6
2 番目のブックを表示 |
 |
図7
2 番目のブックにシートを挿入
|
リスト3
エクセル操作フォームEx を使用しないで複数のブックを開いて操作 |
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;
type
TForm1 = class(TForm)
Button1: TButton;
procedure Button1Click(Sender: TObject);
private
{ Private 宣言 }
public
{ Public 宣言 }
end;
var
Form1: TForm1;
implementation
uses ComObj;
{$R *.dfm}
//=============================================================================
// 複数のブックを表示
// エクセル操作フォームを使用しない場合
// TExcelApplicationを使用してもよいが、メソッド類の引数を省略したいので、最初
// からCreateOleObjectを使用して、OleVariant型で扱うことにする
//=============================================================================
procedure TForm1.Button1Click(Sender: TObject);
var
objExcelApp : OleVariant;
objExcelBook1 : OleVariant;
objExcelBook2 : OleVariant;
objExcelSheet : OleVariant;
begin
objExcelApp := CreateOleObject('Excel.Application');
objExcelBook1 := objExcelApp.WorkBooks.Open(ExpandFileName('../Book1.xls'));
objExcelSheet := objExcelBook1.WorkSheets[1];
//生成したエクセルを表示
//表示しなくても操作は可能
objExcelApp.Visible := True;
//指定時間後に別のブックを開く
Sleep(3000);
objExcelBook2 := objExcelApp.WorkBooks.Open(ExpandFileName('../Book2.xls'));
//指定時間後に、最初のブックの1番目のシートを新しいブックの2番目のシートの前に挿入
Sleep(3000);
objExcelSheet.copy(Before := objExcelBook2.WorkSheets[2]);
//指定時間後に保存しないで終了
Sleep(3000);
objExcelBook1.Saved := True;
objExcelBook2.Saved := True;
objExcelSheet := Unassigned;
objExcelBook1.Close;
objExcelBook2.Close;
objExcelBook1 := unAssigned;
objExcelBook2 := unAssigned;
objExcelApp.Quit;
objExcelApp := unAssigned;
end;
end.
|