ヘッダー行から変数作成 ⑤ 変数名を任意に変更する

前回は、一旦String型で宣言した変数について、その宣言子や
変数の型を変更してみた。
infoment.hatenablog.com
今日も、前回の続きから。
f:id:Infoment:20201105224944p:plain

現時点では一旦変数名を決めたものの、名前が重複したばかりに、
変数名の後ろに数字が付いてしまうケースが発生している。
f:id:Infoment:20201105225155p:plain
これでは、変数名から内容をうかがい知ることが出来ず都合が悪い。

そこで今回は、リストボックスで選択した任意の変数名を変更してみる。

ユーザーフォーム

まず、新たに以下の部品を追加した。

  1. NewNameTextBox 変更後の文字入力用テキストボックス
  2. RenameButton 上記入力結果をリストボックスに反映
  3. ResetButton 一からやり直したくなった時にリセット

各オブジェクト名については、都合が悪くなり次第変更する。
f:id:Infoment:20201105225628p:plain

さて、まずこの文字修正ボタン、ユーザーフォーム起動時に押すことは無い。
なぜなら起動直後の時点で、リストボックスは選択されていないから。

そこで無用のトラブルを避けるため、起動直後はこのボタンを無効化しておく。

Private Sub UserForm_Initialize()

    ' 選択範囲が1列の場合、このツールを使用する条件不成立とする。
    If UBound(HeaderList) = -1 Then Exit Sub
    
    ' 選択範囲のヘッダー部をリスト表示。
    ItemListBox.List = HeaderList
    
    ' 宣言変更用コンボボックス。
    DeclarationComboBox.List = DeclarationArray

    ' 変数の型変更用コンボボックス。
    TypeComboBox.List = TypeArray
    
    ' 文字修正ボタンを無効化 ※現時点でListBox未選択のため。
    RenameButton.Enabled = False      ' <---- 今回追加
    
End Sub

上記と同じ理由から、テキストボックスが空白の時も、同ボタンは
押せないようにしておこう。

' 「選択行の変更後文字」入力用テキストボックス。
' 未入力の場合、文字修正ボタンを無効化する。
Private Sub NewNameTextBox_Change()
    If NewNameTextBox = vbNullString Then
        RenameButton.Enabled = False
    Else
        RenameButton.Enabled = True
    End If
End Sub

ついでに、前回の「全解除」ボタンを押したときも。

' 全解除ボタン。
Private Sub AllUnselectButton_Click()
    ' 複数選択の可否を切り替えると、選択が解除されることを利用。
    ItemListBox.MultiSelect = fmMultiSelectSingle
    ItemListBox.MultiSelect = fmMultiSelectMulti
    
    ' 名前変更用テキストボックスをクリア。
    NewNameTextBox.Value = vbNullString      ' <---- 今回追加
End Sub

リストボックス選択時、選択された変数名がテキストボックスにセットされるようにしたい。なぜなら、元の名前を少しだけ変えるケースが多々あるから。

加えて、二つ以上の変数が選択された場合は、名前の変更をさせてはいけない。
なぜなら、同じ名前の変数が複数できてしまうから(エラー発生)。
そこでこの場合は、名前変更ボタンを無効にしておこう。

' 表のラベルは、そのままの使用に適さない場合がある。
' これを修正するために、リストボックスで一旦選択し、
' その値をテキストボックスに表示させている。
Private Sub ItemListBox_MouseUp(ByVal Button As Integer, ByVal Shift As Integer, ByVal X As Single, ByVal Y As Single)
    Select Case ItemListBox.MultiSelect
        Case fmMultiSelect.fmMultiSelectSingle
            NewNameTextBox = ItemListBox.Value
        Case fmMultiSelect.fmMultiSelectMulti
            Dim i As Long
            Dim SelectedIndex As Long
            Dim Counter As Long
                For i = 0 To ItemListBox.ListCount - 1
                    If ItemListBox.Selected(i) Then
                        Counter = Counter + 1
                        SelectedIndex = i
                    End If
                    
                    ' 複数選択が判明した時点で、処理を抜ける。
                    If Counter >= 2 Then
                        RenameButton.Enabled = False
                        Exit Sub
                    End If
                Next
                
                RenameButton.Enabled = True
                Select Case ItemListBox.ColumnCount
                    Case 1
                        NewNameTextBox = ItemListBox.List(SelectedIndex, 0)
                    Case Else
                        NewNameTextBox = ItemListBox.List(SelectedIndex, 1)
                End Select
    End Select
End Sub

これでようやく、文字修正ボタンが押せる。先ほどと同じ理由から、修正結果が
他の変数名と重複しては不味い。回避策を盛り込んでおこう。

' 文字修正ボタン。
' 「選択行の変更後文字」テキストボックスに入力された値を、
' リストボックスの表示に反映させている。
Private Sub RenameButton_Click()
    Dim i As Long
        For i = 0 To ItemListBox.ListCount - 1
            Select Case i
                ' 名称を変更しない場合、自分自身と重複することを回避。
                Case ItemListBox.ListIndex
                
                ' リストボックスで選択されていない項目について確認。
                ' 全角/半角の影響を受けないよう、vbBinaryCompareを引数に充てている。
                ' ※StrCompで両者が一致した場合の戻り値=0。
                Case Else
                    If StrComp(ItemListBox.List(i), NewNameTextBox.Value, vbBinaryCompare) = 0 Then
                        MsgBox "変更後の名称が既存名称と重複しています。"
                        Exit Sub
                    End If
            End Select
        Next
        Select Case ItemListBox.ColumnCount
            Case 1
                ItemListBox.List(ItemListBox.ListIndex, 0) = NewNameTextBox.Value
            Case Else
                ItemListBox.List(ItemListBox.ListIndex, 1) = NewNameTextBox.Value
        End Select
End Sub

そして最後に、リセットボタンで初期状態に戻す。
増やした列数を元に戻しておかないと、自分で作成したマクロの都合により
エラーが発生するので、注意が必要だ。

' 選択範囲のラベル行をリストボックスにセット。
Private Sub ResetButton_Click()
    With ItemListBox
        .List = HeaderList
        .ColumnCount = 1
    End With
End Sub
結果確認

それでは、実際に確認してみよう。
確認する動作は、以下の3つ。

  1. 状況に応じて、文字修正ボタンの有効/無効が切り替わっているか。
  2. 入力した文字が、新たな変数名として正しく反映されているか。
  3. リセットボタンは機能しているか。

上記の確認結果がこちら。
f:id:Infoment:20201105232002g:plain

今回も、想定通りの結果を得ることが出来た。

次回は、何だかんだで列が増えてしまい、まともに動かなくなってしまった
クリップボードへコピー」ボタンの修正などに挑戦です。

参考まで。