Excel VBA質問箱 IV

当質問箱は、有志のボランティア精神のおかげで成り立っています。
問題が解決したら、必ずお礼をしましょうね。
本サイトの基本方針をまとめました。こちら をご一読ください。

投稿種別の選択が必要です。ご注意ください。
迷惑投稿防止のため、URLの入力を制限しています。ご了承ください。


12835 / 13646 ツリー ←次へ | 前へ→

【8390】windowsAPIのSHBrowseForFolder 初心者 03/10/14(火) 16:54 質問
【8394】Re:windowsAPIのSHBrowseForFolder INA 03/10/14(火) 17:32 回答
【8400】Re:windowsAPIのSHBrowseForFolder 初心者 03/10/14(火) 19:05 お礼
【8401】Re:windowsAPIのSHBrowseForFolder INA 03/10/14(火) 20:47 回答
【8398】Re:windowsAPIのSHBrowseForFolder ichinose 03/10/14(火) 18:19 回答
【8399】Re:windowsAPIのSHBrowseForFolder 初心者 03/10/14(火) 19:01 お礼

【8390】windowsAPIのSHBrowseForFolder
質問  初心者  - 03/10/14(火) 16:54 -

引用なし
パスワード
   本日も宜しくお願い致します。

WindowsAPIのSHBrowseForFolderを使用して、
ダイアログを表示によるフォルダ選択を行う際、
「Esc」ボタンにてキャンセルするとエラーが発生します。
しかし、1ステップずつ実行すると、エラーにはなりません。

1.エラーになるパターン
シート上のコマンドボタンクリック→モジュール呼出「GetFoldName」
→シート上のセルに取得値セット

2.エラーが発生しないパターン
シート上のコマンドボタンクリック→ユーザーフォーム(実行ボタンのみ付加)表示
→ユーザーフォームのボタンクリック→モジュール呼出「GetFoldName」
ユーザーフォームUnload→シート上のセルに取得値セット

一般的には、シートから直接モジュールを呼び出すというやり方は
使用されないのでしょうか?
若しくは、回避策があるのでしょうか?

※機能の検証をしていたので、他の処理は書かれていません。

(シートロジック)
Private Sub Button_Click()
 Dim FoldName as String
  FoldName = GetFoldName()
End Sub

(標準モジュール)
http://homepage1.nifty.com/OkaLab/Program/VbTips01.html#01
を参照したAPIを標準モジュールに宣言

Function GetFoldName() As String
  Dim buf     As String * 260
  Dim buf2    As String * 260
  Dim Ret     As Long
  Dim Operation  As BROWSEINFO
  
  With Operation
    .pidlRoot = 0
    .pszDisplayName = Space(Len(sbuf))
    .hwndOwner = FindWindow("XLMAIN", Application.Caption)
    .lpszTitle = ""
    .ulFlags = &H3
  End With
  
  Ret = SHBrowseForFolder(Operation)  ←デバックではここで黄色になります
  If Ret = 0 Then Exit Function
  
  SHGetPathFromIDList ByVal Ret, ByVal sbuf
  GetFolderName = Left(sbuf, InStr(sbuf, vbNullChar) - 1)
  If Right(F_GetFolderName, 1) = "\" Then
    GetFolderName = Left(sbuf, InStr(sbuf, vbNullChar) - 2)
  End If
End Function

ご存知の方、ご教授の程宜しくお願い致します。

【8394】Re:windowsAPIのSHBrowseForFolder
回答  INA  - 03/10/14(火) 17:32 -

引用なし
パスワード
   WSHのサンプルです。 ご参考までに・・・

Sub Sample()
Dim myObj As Object
  
  Set myObj = CreateObject("Shell.Application"). _
    BrowseForFolder(0, "フォルダを選択してください", 0)
  
  If myObj Is Nothing Then
    MsgBox "キャンセルされました。"
    Exit Sub
  Else
    MsgBox myObj.Items.Item.Path & Chr(13) & " が選択されたパスです。"
  End If
End Sub

【8398】Re:windowsAPIのSHBrowseForFolder
回答  ichinose  - 03/10/14(火) 18:19 -

引用なし
パスワード
   ▼初心者 さん:
こんばんは。
私もフォルダ選択に関しては、INAさんの手法で行っていますが、
それはそれとして・・・・。

Escキーは、Excelでは、特殊なキーになっていますので、
これの処理をいれてみました。

>本日も宜しくお願い致します。
>
>WindowsAPIのSHBrowseForFolderを使用して、
>ダイアログを表示によるフォルダ選択を行う際、
>「Esc」ボタンにてキャンセルするとエラーが発生します。
>しかし、1ステップずつ実行すると、エラーにはなりません。
>
>1.エラーになるパターン
>シート上のコマンドボタンクリック→モジュール呼出「GetFoldName」
>→シート上のセルに取得値セット
>
>2.エラーが発生しないパターン
>シート上のコマンドボタンクリック→ユーザーフォーム(実行ボタンのみ付加)表示
>→ユーザーフォームのボタンクリック→モジュール呼出「GetFoldName」
>ユーザーフォームUnload→シート上のセルに取得値セット
>
>一般的には、シートから直接モジュールを呼び出すというやり方は
>使用されないのでしょうか?
>若しくは、回避策があるのでしょうか?
>
>※機能の検証をしていたので、他の処理は書かれていません。
>
>(シートロジック)
>Private Sub Button_Click()
> Dim FoldName as String
>  FoldName = GetFoldName()
>End Sub
>
>(標準モジュール)
>http://homepage1.nifty.com/OkaLab/Program/VbTips01.html#01
>を参照したAPIを標準モジュールに宣言
>
Function GetFoldName() As String
  Dim buf     As String * 260
  Dim buf2    As String * 260
  Dim Ret     As Long
  Dim Operation  As BROWSEINFO
  Dim sbuf As String
  With Operation
    .pidlRoot = 0
    .hwndOwner = FindWindow("XLMAIN", Application.Caption)
    .lpszTitle = ""
    .ulFlags = &H3
  End With
  Application.EnableCancelKey = xlDisabled '*******
  Ret = SHBrowseForFolder(Operation)  '←デバックではここで黄色になります
  If Ret = 0 Then Exit Function
  Application.EnableCancelKey = xlInterrupt '*******
  sbuf = String$(MAX_PATH, vbNullChar)
  SHGetPathFromIDList ByVal Ret, ByVal sbuf
  'CoTaskMemFree Ret
  GetFoldName = Left(sbuf, InStr(sbuf, vbNullChar) - 1)
  If Right(GetFoldName, 1) = "\" Then
    GetFoldName = Left(sbuf, InStr(sbuf, vbNullChar) - 2)
  End If
End Function

とすると、Escでもエラーは起きませんでした。


>ご存知の方、ご教授の程宜しくお願い致します。

【8399】Re:windowsAPIのSHBrowseForFolder
お礼  初心者  - 03/10/14(火) 19:01 -

引用なし
パスワード
   ▼ichinose さん:

>  Application.EnableCancelKey = xlDisabled '*******
>  Ret = SHBrowseForFolder(Operation)  '←デバックではここで黄色になります
>  If Ret = 0 Then Exit Function
>  Application.EnableCancelKey = xlInterrupt '*******
>
>とすると、Escでもエラーは起きませんでした。

おっしゃる通り、エラーはなくなりました。
ありがとうございました。

【8400】Re:windowsAPIのSHBrowseForFolder
お礼  初心者  - 03/10/14(火) 19:05 -

引用なし
パスワード
   ▼INA さん:
>WSHのサンプルです。 ご参考までに・・・

回答ありがとうございます。
教えて頂いたやり方が一般的なのでしょうか?

「CreateObject」は初めて目にしたので、現在、頂いたサンプルと
ヘルプを調べながら勉強しています。
これを機会にCreateObjectもしっかり習得しておきたいと思います。
ありがとうございました。

【8401】Re:windowsAPIのSHBrowseForFolder
回答  INA  - 03/10/14(火) 20:47 -

引用なし
パスワード
   >これを機会にCreateObjectもしっかり習得しておきたいと思います。
Shell.Application や WSH で調べてみて下さい。

12835 / 13646 ツリー ←次へ | 前へ→
ページ:  ┃  記事番号:
2610219
(SS)C-BOARD v3.8 is Free