Access2003で作成したテーブルをExcelに出力し、そのファイルをAccessから開き、罫線や列幅等フォーマットを自動的に整え、表示します。表示中にデータ確認し、印刷等の処理を行い、閉じて、またAccessの操作に戻りたいと思います。
この際、アクセスで設定したエクセルのオブジェクト変数をCloseしてしまうと、エクセル画面が閉じられてしまう為、AccessモジュールでのClose処理を行わないままとなっています。この為か、引き続いて条件を変えてエクセルに出力して、同様の処理を行うと、AccessモジュールからのExcelの自動フォーマット化が行われなくなってしまいます。Accessを再起動すれば、正常に処理できるので、オブジェクト変数のClose未処理が原因と考えています。
このような場合、一般にはどのように処理されているのでしょうか?Excel画面表示後、DoループDoEvents関数で待ち状態とし、ボタン操作でExcel操作の終了を知らせて、オブジェクト変数のClose処理を行えばいいのかと思いますが、一般にはどのように処理されているものなのかご教示下さい。
No.3ベストアンサー
- 回答日時:
ANO.1,2です。
>繰り返し、エクセルファイルを作成する試験を行ったところ、オブジェクト変数のclose処理を行ったのに改善されませんでした。
とは、私も意外でした。
なにか他に悪さをしている処理があるのでしょうけど、
ちょっと見当がつかないです。
ただ、最後に1個だけ、
・・・
XLWS.Select
With ActiveSheet.PageSetup
・・・
With XLWS.PageSetup
に変えても動いたと思うのですが、
これでやってみてもだめでしょうか?
(
例えばExcel自体が2個立ち上がっていると
With ActiveSheet.PageSetup
とすると、どちらのExcel?ってことになるように思われますので。
)
この回答への補足
ご教示いただいたように冒頭にXLWS.とXLWS.Application.を付加して実行してみました。
当初のコマンドラインは、クリアできましたが、後の方のRangeのところ(下記参照)でエラーとなりました。()内のSelectionの指定方法ではないかと思います。他のSelectionは、XLWS.Application.とすることでクリアしています。Range()内のSelectionは、この方法では、クリアできませんでした。
一回目の処理は、問題なく出来ています。アクセスモジュールからの実行に無理があるのでしょうか?
With XLWS.PageSetup
.PrintTitleRows = "$1:$1"
.PrintTitleColumns = ""
End With
XLWS.Columns("A:A").Select '1列目列削除
XLWS.Application.Selection.Delete Shift:=xlToLeft
XLWS.PageSetup.PrintArea = ""
With XLWS.PageSetup 'ページ書式設定
.LeftHeader = ""
・・・
.PrintErrors = xlPrintErrorsDisplayed
End With
XLWS.Range("A1").Select '罫線設定
XLWS.Range(Selection, ActiveCell.SpecialCells(xlLastCell)).Select 'ここでNo.1004のエラーとなりました。
XLWS.Application.Selection.Borders(xlDiagonalDown).LineStyle = xlNone
XLWS.Application.Selection.Borders(xlDiagonalUp).LineStyle = xlNone
XLWS.Range("A1").select
XLWS.Range(Selection, ActiveCell.SpecialCells(xlLastCell)).Select を
With XLWS
.Range(.Cells(1, 1), .Cells(1, 1).SpecialCells(xlLastCell)).Select
End With
に変えて確認したところ、問題解決しました。
今回は、種々ご教示、ご検討頂き有難う御座いました。厚く御礼申し上げます。
No.2
- 回答日時:
ANo.1です。
補足に書いていただいたソース見ました。
イメージつかめました。
strFilename は毎回同じですか?
毎回同じならば、
必ず、Excelを終了してから、Accessのほうを実行しているならばいいのですが、
Excelを閉じずに動かしてしまうと、おかしなことがおきそうな気がします。
それがあるので、strFilename は毎回違うという前提にして話をします。
XLWS.Visible = True
にして、Excel側で手操作したいのだが、次の処理が動いてしまう、
したがって、続きに、
Set XLAPP = Nothing
Set XLWB = Nothing
Set XLWS = Nothing
と書いてExcelをAccessから切り離している(ように見えますが、本当に切り離せるのかは不明。)
私なら、
XLSWBを保存して、XLSWBをCloseし、XLAPPをCloseし、
set xxx = nothingを実行します。
で、次に、
ShellでExcelを起動します。
(Shellで起動したら最初からAccessと切り離されているため、相互に悪さすることがない。)
Shell ( "C:\Program Files\Microsoft Office\OFFICE11\EXCEL.EXE " & strFilename
,vbNormalFocus)
という感じです。
ただ、ネックは、EXCEL.EXEのパスがまちまちであること。
(探せはどこかにパス名の取得方法があるのかもしれませんが。)
参考文献:
http://www.accessclub.jp/vbakaisetu/49.html
※これをするとExcelが完全に切り離されるので、Excelを終わらずに、次々とAccessの処理を
してしまい大量にExcelが起動されたままとなる可能性はあります。
(操作、運用上の問題なので、操作、運用でカバーしてもらうべきでしょう。)
>Excel画面表示後、DoループDoEvents関数で待ち状態とし、
>ボタン操作でExcel操作の終了を知らせて、
>オブジェクト変数のClose処理を行えばいいのかと思いますが、
確かにそうかもしれませんし、
他にも考えられる手はいくつかあるのですが、
いずれもAccess側の負荷が・・・。
(Do loopまわすと負荷がかかるので、タイマ割り込みとかの方がいいけど、タイムラグがでる。)
いっそ、
Set XLAPP = Nothing
Set XLWB = Nothing
Set XLWS = Nothing
もしないで、このボタンの処理の最初とプログラムの終了前の処理で、
if XLAPP is not nothing then
XLWB.close
XLAPP.close
Set XLAPP = Nothing
Set XLWB = Nothing
Set XLWS = Nothing
end if
が出来たかどうかわかりませんが、ダメでも、
XLAPP is not nothing の変わりにフラグでも用意すればできるはず。
という感じで終了させたら?とも思いますが、
・・・Excel側で終了させてしまってこの処理が動くとエラーになりそうです。
ならば、いっそ、
On Error Resume Next
XLWB.close
XLAPP.close
Set XLAPP = Nothing
Set XLWB = Nothing
Set XLWS = Nothing
On Error goto 0
としたら?というのもありますが。
(但し、この場合のエラーがOn Error Resume Nextで処理してくれるかは確認必要。)
以上どこまで役に立つ情報かわかりませんが、ご参考まで。
(今日はもう遅いですので検証とかする時間がとれないです。2003の環境はあるので、
うまくいかないようなら、明日以後にでもこちらでも試してみます。)
この回答への補足
詳細にご教示頂き、感謝いたします。
ご推奨頂いたShell関数を使用する方法で確認致しました。
下記のように、プログラム変更したところ、希望どおりの処理ができました。
Excelは、2010を使用しており、フォルダをOffice14に変えています。
取り急ぎ、状況報告です。更に、問題ないか確認してみます。
'XLWS.Visible = True
XLWB.Save
XLWB.Close
XLAPP.Quit
Set XLAPP = Nothing
Set XLWB = Nothing
Set XLWS = Nothing
Shell "C:\Program Files\Microsoft Office\OFFICE14\EXCEL.EXE " & strFileName, vbNormalFocus
End Sub
繰り返し、エクセルファイルを作成する試験を行ったところ、オブジェクト変数のclose処理を行ったのに改善されませんでした。
With ActiveSheet.PageSetup
.PrintTitleRows = "$1:$1"
.PrintTitleColumns = ""
End With
上記1行目で、「91:オブジェクト変数又はWithブロック変数が設定されていません。」というエラーが起こり、2回目以降フォーマット化を行う事が出来ませんでした。
今回は、Shell関数の使用方法をご教示頂き有難うございました。予想に反し、解決に至りませんでしたが、またよろしくお願い申し上げます。もう少し解決法を検討後、改めて質問させて頂く事に致します。
有難う御座いました。
No.1
- 回答日時:
どうやってExcelを制御しているのかわからないのでピントハズレかもしれませんが
(プログラムソースの関連する部分でも書いてもらうとわかりやすいかと。)
>アクセスで設定したエクセルのオブジェクト変数をCloseしてしまうと
ではなくって、エクセルで開いているブックをCloseすると思います。
そして、アクセスのプログラムの最後で、エクセルをCloseする。
(エクセルのCloseは、しておかないとメモリリークの原因になりかねないので。
・・・なるとは限りませんが。)
この回答への補足
早速ご検討頂きありがとう御座います。
コードの主要部分は、下記のようになっております。
Public Sub ExcelMaking(QueryName As String)
Dim strFileName As String
Dim XLAPP As Excel.Application
Dim XLWB As Excel.Workbook
Dim XLWS As Excel.Worksheet
strFilename= ファイルパス名
DoCmd.TransferSpreadsheet acExport, acSpreadsheetTypeExcel9, QueryName, strFileName
Set XLAPP = CreateObject("Excel.Application")
Set XLWB = XLAPP.Workbooks.Open(strFileName)
Set XLWS = XLWB.Worksheets(1)
XLAPP.Visible = True
XLWS.Select
With ActiveSheet.PageSetup
.PrintTitleRows = "$1:$1"
.PrintTitleColumns = ""
End With
・・・エクセル外観のフォーマット処理
XLWS.Visible = True 'ここでフォーマット後のシートを画面表示させます。ここで、表示確認や印刷を行います。
Set XLAPP = Nothing 'プログラムはそのまま実行されていくので、画面表示を残す為、Closeせずに、
Set XLWB = Nothing ’取りあえずオブジェクト変数にNothingを代入しています。
Set XLWS = Nothing
End Sub
以上のようなプログラムで、本来Nothing設定前に、XLAPP、XLWB、XLWSをCloseする必要があると思うのですが、これを行うと、エクセル画面を確認できないので、こんなことをしてしまっています。
エクセル画面を表示させた状態で、オブジェクト変数を適切に処置するにはどうすればよいでしょうか?
よろしくお願い致します。
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
似たような質問が見つかりました
- その他(データベース) Accessフォームからパラメーターで表示したレコードを指定のExcelのセルへ転送する方法について 2 2022/08/22 18:04
- Visual Basic(VBA) ExcelからAccessのテーブルに書き込む時に時間がかかる 1 2022/10/14 20:38
- Visual Basic(VBA) vba メモリ節約 3 2022/09/16 21:45
- Visual Basic(VBA) エクセルのマクロで対象ごとにシート分けしてその内容をセルに書き込みたい 9 2022/08/24 13:23
- Excel(エクセル) EXCELの外部データ取得ができない 1 2023/03/23 09:03
- その他(データベース) Microsoft Accessについて 1 2022/06/06 16:20
- Excel(エクセル) Excel VBAどこが間違ってますか? 4 2023/07/17 10:04
- Access(アクセス) Access 登録ボタンからサブフォームの更新 1 2022/07/22 10:23
- Visual Basic(VBA) 3つのプロシージャをまとめたら実行時エラー発生で対応不能 6 2022/05/17 01:47
- Visual Basic(VBA) VBAが止まります。 2 2022/09/02 14:02
関連するカテゴリからQ&Aを探す
おすすめ情報
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
DELETE文でFROM句を省略した場合
-
DBリンクエラーについて
-
accessでイベントを中止するよ...
-
RDBのテーブル種類の違い
-
処理速度について(UPDATE)
-
PL/SQLの平行処理について
-
[性能改善]AccessのDBに大量の...
-
カーソルについて
-
チューニング対象のSQLの見つけ...
-
stored procedureの引数について
-
C#でトランザクション開始後参...
-
他の処理でselectさせないよう...
-
カーソルでのデータ取得
-
同じSELECT文同士でのデ...
-
データを削除しても表領域の使...
-
Viewにインデックスは張れ...
-
異なるスキーマからデータを抽...
-
viewのバックアップ
-
INDEXの無効化
-
CLOB型へのINSERT
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
DELETE文でFROM句を省略した場合
-
RDBのテーブル種類の違い
-
他の処理でselectさせないよう...
-
object browser で処理を中断す...
-
同じSELECT文同士でのデ...
-
[性能改善]AccessのDBに大量の...
-
accessでイベントを中止するよ...
-
年度毎にシーケンスの初期化?
-
DBリンクエラーについて
-
PL/SQLの平行処理について
-
Truncate以外で高速にテーブル...
-
同一レコード更新時の排他制御
-
チューニング対象のSQLの見つけ...
-
統計情報の取得=コミットですか?
-
ASPからのSQL文でエラーが発生
-
処理速度の見積もり時間について。
-
Oracleから見たOracleの優位性(...
-
カーソルについて
-
トランザクションのデータ件数...
-
stored procedureの引数について
おすすめ情報