[ 初めての方へ | 一覧(最新更新順) | 全文検索 | 過去ログ ]
『【ユーザーフォーム】ラベルのクリックイベントのまとめ方』(おおとりさん)
いつも参考にさせていただいております。
ユーザーフォームのラベルのイベント処理について
ご教示いただけますでしょうか。
ユーザーフォーム上にラベルが20個ほどあり、
それぞれにクリックイベントを作成したいと考えております。
イベント処理の中身は同じで
ラベル1がクリックされたらテキストボックス1〜10を処理
ラベル2がクリックされたらテキストボックス11〜20を処理
・・・
といった流れです。
クリックイベントのまとめ方、クリックされたラベルの取得の仕方について
ご教示いただけますと幸いです。
以上、宜しくお願いいたします。
< 使用 Excel:Excel2016、使用 OS:Windows10 >
>ユーザーフォーム上にラベルが20個ほどあり、 >ラベル1がクリックされたらテキストボックス1〜10を処理 >ラベル2がクリックされたらテキストボックス11〜20を処理 でラベルが3〜20をクリックした時、テキストボックスとの関連はどうなるのですか。 ラベル1=テキストボックス1ではないのですか。 (・・・) 2022/08/09(火) 11:06
>クリックイベントのまとめ方、クリックされたラベルの取得の仕方 とりあえず↑だけ考えて...
'正攻法(共通サブに自身を渡す) Option Explicit
Private WithEvents Lbl1 As MSForms.Label Private WithEvents Lbl2 As MSForms.Label Private WithEvents Lbl3 As MSForms.Label Private WithEvents Lbl4 As MSForms.Label Private WithEvents Lbl5 As MSForms.Label Private WithEvents Lbl6 As MSForms.Label
Private Sub Lbl1_Click() LblsClicked Lbl1 End Sub Private Sub Lbl2_Click() LblsClicked Lbl2 End Sub Private Sub Lbl3_Click() LblsClicked Lbl3 End Sub Private Sub Lbl4_Click() LblsClicked Lbl4 End Sub Private Sub Lbl5_Click() LblsClicked Lbl5 End Sub Private Sub Lbl6_Click() LblsClicked Lbl6 End Sub
Private Sub LblsClicked(l As MSForms.Label) MsgBox l.Name End Sub
Private Sub UserForm_Initialize() Set Lbl1 = Me.Controls.Add("Forms.Label.1", "Lbl1") Set Lbl2 = Me.Controls.Add("Forms.Label.1", "Lbl2") Set Lbl3 = Me.Controls.Add("Forms.Label.1", "Lbl3") Set Lbl4 = Me.Controls.Add("Forms.Label.1", "Lbl4") Set Lbl5 = Me.Controls.Add("Forms.Label.1", "Lbl5") Set Lbl6 = Me.Controls.Add("Forms.Label.1", "Lbl6") Lbl1.Top = 3 + Lbl1.Height * 0 Lbl2.Top = 3 + Lbl1.Height * 1 Lbl3.Top = 3 + Lbl1.Height * 2 Lbl4.Top = 3 + Lbl1.Height * 3 Lbl5.Top = 3 + Lbl1.Height * 4 Lbl6.Top = 3 + Lbl1.Height * 5 Dim i As Long For i = 1 To 6 With Me.Controls("Lbl" & i) .Caption = i .SpecialEffect = fmSpecialEffectRaised End With Next End Sub
'お遊び(透明なラベルを上にかぶせてクリック位置から逆算する) Option Explicit
Private Lbl1 As MSForms.Label Private Lbl2 As MSForms.Label Private Lbl3 As MSForms.Label Private Lbl4 As MSForms.Label Private Lbl5 As MSForms.Label Private Lbl6 As MSForms.Label Private WithEvents LblCv As MSForms.Label
Private Sub LblCv_MouseDown(ByVal Button As Integer, ByVal Shift As Integer, ByVal X As Single, ByVal Y As Single) If X < 0 Or Y < 0 Then Exit Sub If X > LblCv.Width Or Y > LblCv.Height Then Exit Sub If Button = 1 Then Dim h As Single h = Lbl1.Height MsgBox Int(Y / h) + 1 & "番" End If End Sub
Private Sub UserForm_Initialize() Set Lbl1 = Me.Controls.Add("Forms.Label.1", "Lbl1") Set Lbl2 = Me.Controls.Add("Forms.Label.1", "Lbl2") Set Lbl3 = Me.Controls.Add("Forms.Label.1", "Lbl3") Set Lbl4 = Me.Controls.Add("Forms.Label.1", "Lbl4") Set Lbl5 = Me.Controls.Add("Forms.Label.1", "Lbl5") Set Lbl6 = Me.Controls.Add("Forms.Label.1", "Lbl6") Lbl1.Top = 3 + Lbl1.Height * 0 Lbl2.Top = 3 + Lbl1.Height * 1 Lbl3.Top = 3 + Lbl1.Height * 2 Lbl4.Top = 3 + Lbl1.Height * 3 Lbl5.Top = 3 + Lbl1.Height * 4 Lbl6.Top = 3 + Lbl1.Height * 5 Dim i As Long For i = 1 To 6 With Me.Controls("Lbl" & i) .Caption = i .SpecialEffect = fmSpecialEffectRaised End With Next Set LblCv = Me.Controls.Add("Forms.Label.1", "LblCv") LblCv.Top = 3 LblCv.Height = LblCv.Height * 6 LblCv.BackStyle = fmBackStyleTransparent End Sub
あとクラスモジュール使ってイベントをまとめる手法もありますね。 (モジュール分かれるから個人的には好きではないですが ^^;)
(白茶) 2022/08/09(火) 11:20
>ユーザーフォーム上にラベルが20個ほどあり、 >ラベル1がクリックされたらテキストボックス1〜10を処理 >ラベル2がクリックされたらテキストボックス11〜20を処理 でラベルが3〜20をクリックした時、テキストボックスとの関連はどうなるのですか。 ラベル1=テキストボックス1ではないのですか。 (・・・)
返信ありがとうございます。
ラベル3以降もテキストボックス21〜30と10単位で増加していきます。
処理の中身はラベルをクリックしたら、クリックしたらラベルの文字色(forecolor)を赤、
ラベルと関係のないテキストボックスは入力不可 enabled = False、Locked = True と処理しています。
例)
ラベル1をクリック
ラベル1の文字色を赤
ラベル2〜20の文字色を黒
テキストボックス1〜10を Enabled = True Locked = False
テキストボックス11〜200を Enabled = False Locked = True
上記の処理をラベル分作成するのが大変なため、まとめたいと考えております。
(おおとりさん) 2022/08/09(火) 11:51
返信、コードの提案ありがとうございます。
正攻法のコードで処理が可能か試させていただきます。
(おおとりさん) 2022/08/09(火) 11:53
Public sumControls() As New UserForm1
Sub SummationControls()
' Dim uf As UserForm Dim ctrl As Control Dim cnt As Long, idx As Long Dim ctrlName As String
' Set uf = UserForm1
With uf cnt = .Controls.Count For idx = 1 To cnt Set ctrl = .Controls(idx - 1) ctrlName = ctrl.Name With Module1.sumControls(idx) Select Case True Case ctrlName Like "Label*" Set .Lbl = ctrl Case ctrlName Like "Text*" Set .Txt = ctrl Case Else End Select End With Next idx End With
End Sub
でユーザーフォームUserForm1に
Public WithEvents Lbl As MSForms.Label
Public WithEvents Txt As MSForms.TextBox
Private Sub Lbl_Click()
'ここに処理を記述 'Lbl.index でそれぞれのインデックスが取得できる
End Sub
Private Sub Txt_Click()
'ここに処理を記述 'Txt.index でそれぞれのインデックスが取得できる
End Sub
ではどうですか?
(ngk) 2022/08/09(火) 13:47
ユーザーフォーム上にフレーム「Frame1」を配置します。その中に、オプションボタンを20個配置します。(OptionButton1 〜 OptionButton20)
フレーム内にオプションボタンを配置することでグループ化されてその中の一つだけ選択できるようになります。
テキストボックス名は Textbox1 〜 Textbox200 とします。
Private Sub OptionButton1_Click() optCheck End Sub
Private Sub OptionButton2_Click() optCheck End Sub
'中略・・・・
Private Sub OptionButton20_Click() optCheck End Sub
Public Sub optCheck() Dim opt As Control, i As Long, j As Long
For Each opt In Me.Frame1.Controls If opt.Value = True Then opt.ForeColor = vbRed For i = 1 To 200 With Me.Controls("Textbox" & i) .Enabled = False: .Locked = True End With Next j = Mid(opt.Name, 13) * 10 - 10 For i = 1 To 10 With Me.Controls("Textbox" & i + j) .Enabled = True: .Locked = False End With Next Else opt.ForeColor = vbBlack End If Next End Sub
もし、フレーム内に配置したくないという場合、オプションボタンの GroupNameプロパティを同じに設定すればグループ化されます。
(hatena) 2022/08/09(火) 14:21
ついでに、ありきたりな手法をもうひとつ ^^;
各コントロールのTagプロパティに、あらかじめグループ名を入れておいて そのグループ名をキーにして巡回処理を共通化する。という...
Private CurrentTagStr As String Private Property Get CurrentGroup() As String CurrentGroup = CurrentTagStr End Property Private Property Let CurrentGroup(newGroup As String) If newGroup = CurrentTagStr Then Exit Property CurrentTagStr = newGroup Dim c As Control For Each c In Me.Controls If TypeOf c Is MSForms.Label Then c.ForeColor = IIf(c.Tag = CurrentTagStr, vbRed, &H80000012) If TypeOf c Is MSForms.TextBox Then c.Enabled = CBool(c.Tag = CurrentTagStr) c.Locked = Not c.Enabled End If Next End Property
Private Sub Label1_Click() CurrentGroup = "G1" End Sub Private Sub Label2_Click() CurrentGroup = "G2" End Sub Private Sub Label3_Click() CurrentGroup = "G3" End Sub
(白茶) 2022/08/09(火) 14:24
皆様、コードをご提案いただきありがとうございます。
同じ結果でも多様な方法があると改めて勉強になっております。
私の知識不足で調べてみないとわからない部分もあるため、
ひとつひとつ理解しながら試して最良なコードを探してみます。
合わせてオプションボタンへの変更も検討してみたいと思います。
(おおとりさん) 2022/08/09(火) 14:48
With uf cnt = .Controls.Count Redim module1.sumControls(cnt) ←これ書き忘れてました
For idx = 1 To cnt Set ctrl = .Controls(idx - 1)
(ngk) 2022/08/09(火) 16:12
こんにちは、質問ですが
テキストボックス200個は、UserForm1 に 全部...並んでるんですか?
(あみな) 2022/08/09(火) 16:31
ご丁寧にありがとうございます。
追記しコードを試させていただきます。
(あみな)さん
はい、10列20行の形で並んでいます。
業務の処理上、この形が一番見やすいので上記で配置しています。
テキストボックスの入力処理はfor文とcontrolsで処理が可能なので
今回のクリックイベントの共通化を理解することができればとても楽になります。
(おおとりさん) 2022/08/09(火) 16:56
テキストボックスの配置については10個 * 20 行分といった形なので
10個分を作成したらコピペで配置できたのでそこまで大変ではありませんでした。
購買業務で使用しています。
1品種につき20社分の見積情報から購入先を選定する際に一覧表示できるように作成しています。
伝わりづらければ申し訳ありません。。。
(おおとりさん) 2022/08/09(火) 17:05
AddinBox/擬似からの脱却
http://addinbox.sakura.ne.jp/Breakthrough_P-Ctrl_Arrays.htm
汎用モジュール/clsBPCA を使って
サンプルコード を参考にすれば
かなり楽になると思いますよ。
(clsBPCA 自体は一切編集する必要はありません)
(AddinBox_角田) 2022/08/10(水) 10:32
コメントありがとうございます。
テキストボックスの処理については 処理列とテキストボックスの番号を合わせることで
そこまでコードを書かなくても処理ができております。
(最適なコードであるかはわかりませんが。。。)
例)
UserForm.Controls("textbox" & j).Value = Worksheets.Cells(行, j)
UserForm.Controls("textbox" & j).ControlSource= Worksheets.Cells(行, j)Address(RowAbsolute:=False, ColumnAbsolute:=False)
汎用モジュール/clsBPCA の件、URLまでありがとうございます。
初めて聞く処理のため理解が必要ですが、今回のラベルのクリックイベントでも使用できるかもしれません。
テキストボックスの処理の改善も含め、早速読んでみたいと思います。
(おおとりさん) 2022/08/10(水) 12:28
こんばんは、 テキストボックス200個は、UserForm1 に全部並んでるんですね。
業務では、処理スピードと、見やすさも重要かと 思われるので...やりやすい方法が一番良いのですが
ユーザーフォームの画面が大きいので大迫力だな〜と 想像しております。
そちらの処理と、全画面がわからないので...良し悪しがわかりませんので 一案ではありますが…どうなのでしょうか?^^;
マルチページを使用して、テキストボックスを10個ずつ 処理と、表示をさせることを検討されてはと思ったので 参考程度ですが
私が、「 ファイルなう 」と言うサイトへ… アップロードしたファイルです。 Windowsフォトビューアーで画像だけが閲覧可能です。
クリックイベントでも、オプションボタンでもよいのですが ユーザーフォームの初期画面から、選択して Opt1 を選択
◇1 ダウンロードURL: 購買管理初期値.JPG(53 KB) https://d.kuku.lu/1c9587d49
Opt1 選択後、コマンドボタンクリックから 画面を表示切替して、テキストボックスへ処理反映させたのが
◇2 ダウンロードURL: Opt1.JPG(49 KB) https://d.kuku.lu/c90521478
切替は、購買管理画面に戻り… Opt3 を選択後に表示切替させたのが下記URL
◇3 ダウンロードURL: Opt3.JPG(48 KB) https://d.kuku.lu/fb374b516
◆「 ファイルなう 」運営者情報 くくさま @kukusama https://twitter.com/kukusama
(あみな) 2022/08/10(水) 22:02
200個のデータをすべて一覧表示させておく必要があるのならだめですが、シートには一覧表示されているのなら、なくてもよさそうに思いますがいかがでしょう。
ちなみに、下記のコードの1行目は不要では。ControlSourceでリンクさせれば、セルの値は自動で反映されますので。
UserForm.Controls("textbox" & j).Value = Worksheets.Cells(行, j) UserForm.Controls("textbox" & j).ControlSource= Worksheets.Cells(行, j).Address(RowAbsolute:=False, ColumnAbsolute:=False)
(hatena) 2022/08/11(木) 12:28
オプションボタン20個、テキストボックス20個を配置しておいて、
上記の部分は下記に訂正です。
オプションボタン20個、テキストボックス10個を配置しておいて、
コードとしては下記になります。
Private Sub OptionButton1_Click() optCheck End Sub Private Sub OptionButton2_Click() optCheck End Sub '中略・・・・ Private Sub OptionButton20_Click() optCheck End Sub
Public Sub optCheck() Dim opt As Control, i As Long, j As Long For Each opt In Me.Frame1.Controls If opt.Value = True Then opt.ForeColor = vbRed j = Mid(opt.Name, 13) For i = 1 To 10 Me.Controls("Textbox" & i).ControlSource = Worksheets(1).Cells(i, j).Address(False, False) Next Else opt.ForeColor = vbBlack End If Next End Sub
(hatena) 2022/08/11(木) 12:46
サンプル画面の作成をしていただきありがとうございます。
業務用のエクセルなので直接画面を乗せることができませんが、
200個のテキストボックスがすべて並んだ状態が見やすい形となっています。
10個ずつとなると少し見やすさに欠けてしまう状態となってしまいます。。。
わざわざ作成していただいたのにすみません。。。
(hatena)さん
コメントありがとうございます。
すべてのテキストボックスが並んでいることが最良な形となっています。
シートにも一覧表示されていますがシート画面の状態ですと見づらいため
今回のユーザーフォーム画面を作成しています。
1行目のコード不要の件、ご指摘ありがとうございます。
動作可能か試させていただきます。
皆様に挙げて頂いたコードを読みながら自分が実装できる範囲で作成しております。
現在、以下の形でおおよそ理想な処理ができるようになりました。
Private Sub Label1_Click(): call 購入処理(1): End sub Private Sub Label2_Click(): call 購入処理(2): End sub Private Sub Label3_Click(): call 購入処理(3): End sub
〜 20まで
Private Sub 購入処理(ラベル番号)
select case ラベル番号
case 1 開始番号 = 1 終了番号 = 10 case 2 開始番号 = 11 終了番号 = 20 case 3 開始番号 = 21 終了番号 = 30
〜 20まで
for i = 1 to 200 'テキストボックス処理用
select case i case 開始番号 to 終了番号 該当テキストボックス処理 Else case 非該当テキストボックス処理 end case next
(おおとりさん) 2022/08/12(金) 10:38
[ 一覧(最新更新順) ]
YukiWiki 1.6.7 Copyright (C) 2000,2001 by Hiroshi Yuki.
Modified by kazu.