[ 初めての方へ | 一覧(最新更新順) | 全文検索 | 過去ログ ]
『他のブックの変数を制御』(田吾作)
こんにちは、よろしくお願いいたします。
ブックやアプリケーションの閉じるボタン(×)ではなく、ユーザーフォームの コマンドボタンクリックでブックを閉じるようにしています。
ブック起動時に変数をFalseにし、×ボタンをクリックしても閉じなく、 コマンドボタンをクリックすることによって変数をTrueにし、変数がTrue だったら閉じるようにしています。
−−−−−−−−−−−−−−− '標準モジュール Public clsflg As Boolean
Sub cls()
ThisWorkbook.Saved = True
If Workbooks.Count = 1 Then
Application.Quit
Else
ThisWorkbook.Close
End If
End Sub
'ThisWorkbookモジュール Private Sub Workbook_Open() clsflg = False UserForm1.Show 0 End Sub
Private Sub Workbook_BeforeClose(Cancel As Boolean)
If clsflg = True Then
Call cls
Else
Cancel = True
End If
End Sub
'ユーザーフォーム Private Sub CommandButton1_Click() clsflg = True Call cls End Sub −−−−−−−−−−−−−−−
これは問題なく動いています。
ただ、これだと、開いているブックを他のブックから閉じようとするときに 逆に邪魔になってしまいます。 他のブックは閉じますが、上記のコードを記述してあるブックは閉じずに 残ってしまいます。
たとえば、下記のようなコードで開いているブックを閉じるような場合です。
−−−−−−−−−−−−−−−
Sub wbcls()
Dim mypath As String
Dim wb As Workbook
mypath = ThisWorkbook.FullName
For Each wb In Workbooks
If wb.FullName <> mypath Then
If wb.Saved = True Then wb.Close
End If
Next wb
End Sub
−−−−−−−−−−−−−−−
他のブックから、閉じたいブックの変数「clsflg」をTrueにする、という 操作ができたらブックを閉じることができるように思うのですが、他の ブックの変数を操作する、という方法がわかりません。
全然別のアプローチでもいいのでご教示いただきましたら幸甚です。 よろしくお願いいたします。
< 使用 Excel:Excel2007、使用 OS:WindowsVista >
変数でのハンドリングは、いろいろやっかいなことになるかもしれません。 該当のブックの変数を取得する方法はいくつかありますが、 Sub wbcls() で抽出されたブックが、すべて そのように変数を返す構成になっているか、ただのブックで、そんなことは不要のブックなのかの判断も必要になりますね。 そういった構成になっていないブックに対して変数を取得しようとすると、不都合というかエラーになると思いますし。
1つの方法としては、現在、変数で閉じていいかどうかを制御していることをすべてやめて、 Workbook_Openで。このブックのXボタンそのものを無効にしておく。そうすると、操作者がXボタンをクリックすること、そのものができなくなりますので。
'閉じるボタンの無効化 Private Declare Function GetSystemMenu Lib "user32" (ByVal hWnd As Long, ByVal bRevert As Long) As Long Private Declare Function RemoveMenu Lib "user32" (ByVal hMenu As Long, ByVal nPosition As Long, ByVal wFlags As Long) As Long
Const MF_BYCOMMAND = &H0& Const SC_CLOSE = &HF060
Private Sub Workbook_Open()
Dim hWnd As Long
Dim rtn As Long
hWnd = Application.hWnd
rtn = GetSystemMenu(hWnd, 0)
rtn = RemoveMenu(rtn, SC_CLOSE, MF_BYCOMMAND) ' 閉じるボタンの無効化
End Sub
なお、以下のようなレスキューコードを標準モジュールに書いておくといいかも。
Sub TestClose()
ThisWorkbook.Close True
End Sub
(β) 2015/04/15(水) 09:07
標準モジュールではなく、ThisWorkbookモジュールに当該変数を設置して見ては?
Thisworkbookのモジュールに
public clspermit as boolean
とすれば、
別ブックからでも Workbooks("対象ブック").clspermit=true
このような指定ができます。
標準モジュールにPublic変数は 置かなくてもプログラムは作れます。 いえ、その方がよいです。
(ichinose) 2015/04/15(水) 13:31
当該ブック内に、フラグをFalseにするサブプロシージャを記述して
他ブックから、そのプロシージャをapplication.runで呼び出すのはどうでしょう。
( 佳 ) 2015/04/15(水) 19:43
βさん、ichinoseさん、佳さん、ご回答ありがとうございます。 御三方の方法を試してみました。いずれもうまくいきました。
コードは下記のとおりです。 ※βさんの方法はご教示いただきましたコードをそのまま実行 しました。
最終的にどのようにするかはいろいろ勘案してみます。 ありがとうございました。
閉じる対象のブック
'ThisWorkbookモジュール
Public clsflg As Boolean
Private Sub Workbook_Open() clsflg = False UserForm1.Show 0 End Sub
Private Sub Workbook_BeforeClose(Cancel As Boolean)
If clsflg = True Then
Call cls
Else
Cancel = True
End If
End Sub
'標準モジュール
Sub cls()
Application.WindowState = xlNormal
ThisWorkbook.Saved = True
If Workbooks.Count = 1 Then
Application.Quit
Else
ThisWorkbook.Close
End If
End Sub
Sub flgtrue() ThisWorkbook.clsflg = True End Sub
マクロ実行ブック
'ichinoseさんご教示の方法
Sub wbclsA()
Dim mypath As String
Dim wb As Workbook
mypath = ThisWorkbook.FullName
For Each wb In Workbooks
If wb.FullName <> mypath Then
If wb.Saved = True Then
Err.Clear
On Error Resume Next
wb.clsflg = True
wb.Close
On Error GoTo 0
End If
End If
Next wb
End Sub
'佳さんご教示の方法
Sub wbclsB()
Dim mypath As String
Dim wb As Workbook
mypath = ThisWorkbook.FullName
For Each wb In Workbooks
If wb.FullName <> mypath Then
Application.Run wb.Name & "!flgtrue"
If wb.Saved = True Then wb.Close
End If
Next wb
End Sub
(田吾作) 2015/04/16(木) 00:41
[ 一覧(最新更新順) ]
YukiWiki 1.6.7 Copyright (C) 2000,2001 by Hiroshi Yuki.
Modified by kazu.