質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
VBA

VBAはオブジェクト指向プログラミング言語のひとつで、マクロを作成によりExcelなどのOffice業務を自動化することができます。

VB.NET

Microsoft Visual Basic .NETのことで、Microsoft Visual Basic(VB6)の後継。 .NET環境向けのプログラムを開発することができます。 現在のVB.NETでは、.NET Frameworkを利用して開発を行うことが可能です。

Q&A

解決済

1回答

1411閲覧

モーダルフォームの問題解消のために、VBAで作ったシステムの一部をVB.NETに分担させたい

kujiraSE

総合スコア21

VBA

VBAはオブジェクト指向プログラミング言語のひとつで、マクロを作成によりExcelなどのOffice業務を自動化することができます。

VB.NET

Microsoft Visual Basic .NETのことで、Microsoft Visual Basic(VB6)の後継。 .NET環境向けのプログラムを開発することができます。 現在のVB.NETでは、.NET Frameworkを利用して開発を行うことが可能です。

0グッド

0クリップ

投稿2020/03/19 16:50

編集2020/03/19 17:02

エクセルVBAで開発したエクセルのシステムがあります。
このシステムでは、シート上に設置した多くのコマンドボタンをクリックすることで、ボタンに応じた様々なモーダルフォームを表示し、使用者に諸々の値の入力を促すようになっています。
ただ、このシステムには問題があり、このシステムでモーダルフォームを表示している状態でユーザーが別のエクセルブックを開こうとしても開くことができないことがあったり、既に開いている別のブックのウィンドウをアクティブにしようとすると不具合が出て不安定になるなどの事象が発生しています。
やはり、同時にいくつかのファイルを開くことが多いエクセルで、モーダルフォームを次々に表示するようなシステムを作ったことじたい全体が見えてなかったのではないかと問題になっています。

この弊害への対策として、まず、できる限りモーダルフォームの利用を廃し、ユーザーからの入力を促すだけならほとんどのセルをロックしまくったシートで代用させることを検討しましたが、シートを新設し、多量のテキストボックスを並べて作ってきたフォームをいちいちシートに移していくのも手間だし、いっそ、各フォームだけを集めてVisualBasic.NETでexeファイルを作成してしまえばいいのではないかと思い当たりました。

つまり、元のエクセル.xlsmはフォームを自分で持つことをやめ、必要に応じてパートナーである自作VBNETシステム.exeを(そのとき起動してないなら)起動させて、必要なフォームを表示してもらう、という形にした方がいいのではないか。そうしたら、エクセルとしてはモーダルフォームを出すことはないから、同時に開いている別ブックやそのウィンドウに不当な影響を与えることはないのではないか、と。
これまでエクセルでフォームを表示させていた場面では、これからは、そのエクセルのVBAから自作VBNETシステム.exeを起動させて「あなたが所持している○○というフォームを表示しろ」と命令することにし、なおかつ、「そのフォームの各テキストボックスコントロールの初期値はわがエクセルファイルの××というシートのこのセルの値にしておきなさい」としておく形にし、
逆に自作VB.NET.exeの方では、「フォームにあるこの"決定"コマンドボタンがクリックされたときは、今開かれているはずの相棒エクセル.xlsmの、××というシートの該当セルに、我がフォームのテキストボックスコントロールの値を挿入し、なおかつ、そのエクセルシステムにある○○というプロシージャを実行させて、自らは閉じてしまえ」と命令を書いておけばいいのではないかというアイデアを思いつきました。
すべては、元々のエクセルで作ったシステムの中でフォームを用いないことで「同時に開いている他のエクセルブックさんたちに迷惑をかけない」のが目的です。

私は、VBAの経験だけでVB.NETの経験はまったくありませんが、同じVB仲間だし何とかなるのではないかと、この方法の現実性について調べ始めました。
しかし、必要な情報をすべて得ることはできず、ここで質問させてもらいたいです。

  1. エクセルのVBAから、自分とは別のexeファイル(起動しているかどうかわからない。起動していないなら起動させたうえで)に対し、「○○というフォームを表示させろ。そしてそのフォーム上のコントロールの初期値には我がブックの(非表示のときもある)○○シートの値を取得して設定しろ」という命令が可能なのか

  2. 逆に、VB.NETで作ったexeファイルの方からは、相棒であるはずのエクセル.xlsm(開かれているはず)ファイルのシートから値を取得したり、与えたり、また、そのエクセルにあるプロシージャを実行させるということが可能なのか

  3. そもそも、こうやってフォームだけを別に集めて別exe化するだけで、エクセルの挙動は安定するのか

  4. エクセルVBAのエディタからは、既存のフォームを.frmファイルとして外部保存できるようだが、VB.NETの開発時にこのままそのフォームのデータを取り入れることができるのではないか。けっこう凝って作ったフォームだから、そのままVB.NETの開発に使えればありがたいがどうだろうか

以上4点の疑問が、ネットで調べたかぎりでははっきりしません。
知識のある方、同様の経験のある方、教えていただきたいです。

なお「VBAしかできない素人のくせにVB.NETのコードが書けるのか」という点については、「フォームを表示していくつかのデータをやりとりする程度のものだから、なんとかなるんじゃないか」と楽観しています。

よろしくお願いいたします。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

問題点は、モーダルフォームを開くことで、別ブックの操作に問題がでるということですよね。
ならばモーダルではなくモードレスで開けばいいのでは。
そうすれば別ブックの操作に影響はないはずです。

vba

1 UserForm1.Show vbModeless

ユーザーフォームが開いているとき、自ブックを操作できないようにするには、ユーザーフォームのInitializeですべてのシートに保護をかけて、Terminateで保護を解除すればいいでしょう。

vba

1Private Sub UserForm_Initialize() 2 Dim ws As Worksheet 3 4 For Each ws In ThisWorkbook.Worksheets 5 ws.Protect UserInterfaceOnly:=True 6 ws.EnableSelection = xlNoSelection 7 Next 8End Sub 9 10Private Sub UserForm_Terminate() 11 Dim ws As Worksheet 12 13 For Each ws In ThisWorkbook.Worksheets 14 ws.Unprotect 15 ws.EnableSelection = xlUnlockedCells 16 Next 17End Sub

投稿2020/03/19 20:59

hatena19

総合スコア33715

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

kujiraSE

2020/03/22 04:09

ご回答ありがとうございました! モードレスという設定では、ウィンドウやシートを切り替えているうちに、フォーム自体がシートの下に行ってしまいわけが分からなくもんだと思っていました。 本当に助かりました。ありがとうございました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問