[ 初めての方へ | 一覧(最新更新順) | 全文検索 | 過去ログ ]
『データをコピーして一部の内容を変更して挿入するマクロ』(ふーさん)
工場で生産指示したものをどこに出荷したかを記入するファイルがあります。
A B C D E F G H I J K ・・・ P Q R S 1 2 開始日 指示No 部署1 部署2 部署3 担当 商品ID 品名 指示数量 完成数量 完了日 出荷日 出荷先 出荷数 3 2012/3/1 12345678 AA BB CC 鈴木 1111 ●●● 50000 4 2012/3/2 23456789 AA DD EE 加藤 2222 □□□ 6000
このように入力されていたものを、生産が終わって出荷した時に次のようにデータを追加します。
A B C D E F G H I J K ・・・ P Q R S 1 2 開始日 指示No 部署1 部署2 部署3 担当 商品ID 品名 指示数量 完成数量 完了日 出荷日 出荷先 出荷数 3 2012/3/1 12345678 AA BB CC 鈴木 1111 ●●● 50000 50000 2012/3/7 2012/3/8 あ社 10000 4 2012/3/1 12345678 AA BB CC 鈴木 1111 ●●● * * 2012/3/7 2012/3/9 い社 40000 5 2012/3/2 23456789 AA DD EE 加藤 2222 □□□ 6000
同じものでも出荷先が一か所の場合と複数の場合があり、複数の場合は上記のように元のデータをコピーし、 一部を * にしたり出荷日・出荷先・数量を変更してそのデータに追加・挿入します。
この結果入力をユーザーフォームを使ってできないかと言われました。 ただ、稀に「指示No」が元から重複しているものもあります(商品などは違う)
なので「指示No」をテキストボックスか何かに打ち込んで、商品IDと商品名をリストボックスに表示、 表示されたリストから該当データを選んで出荷結果を入力、出荷先が複数の場合は上記のように 行を挿入してデータを追加…
ということをやりたいのですが、ユーザーフォームはただ単純にテキストボックスに入力して 転記するだけのものしか作ったことがなく、どのようなコードにしたらいいのか途方にくれております。
元のデータの呼び出し方と、データの間に追加のデータを挿入する方法をお教えください。
複数出荷については了解なんだけど、それとは別に、追加出荷分も含めて 入力済みのものの修正・取消ということは考えなくてもいいね?
追記)データ件数は、おおよそ、どれぐらい? ざくっとでいいので。数百?数千?数万?
(ぶらっと)
ぶらっと様 修正・取消は多分目視の方が確実なのでこの場合考えなくて大丈夫です。 データ件数は2〜3千ぐらいです。
あと、リストボックスに表示する時に商品IDと商品名だけでは特定できないかもしれないので「開始日」または「指示数量」まで表示したいです。
(ふーさん)
面白そうなので作って見ました 上手く行かなかったらゴメン
AdvancedFilter(フィルタオプション)を使いますので作業用シートを用意します (上手く動く様なら後で非表示にすれば善いと思います) シート名は「抽出」と言う名前を付けて下さい 「抽出」シートに
A B C D E F G 1 指示No 商品ID 品名 指示数量 指示No
B1 :「指示No」、C1:「商品ID」、D1:「品名」、E1:「指示数量」、G1:「指示No」の列見出しを 「出荷したか」を記入しているシートから列見出しをCopyして下さい (フィルタオプションが神経質な様で、手で記入しない方が善いと思います)
次にUserFormを用意します 各コントロールの配置は以下の様にします 指示No :ComboBox1 開始日 :TextBox1 部署1 :TextBox2 部署2 :TextBox3 部署3 :TextBox4 担当 :TextBox5 商品ID :ComboBox2 品名 :TextBox6 指示数量 :TextBox7 完成数量 :TextBox8 完了日 :TextBox9 出荷日 :TextBox10 出荷先 :TextBox11 出荷数 :TextBox12 更新/追加:CommandButton1 閉じる :CommandButton2 L列〜O列は解らないのでコントロールを配置していません
UserFormのコードモジュールに以下を記述して下さい 尚、出荷シートの名前、列数、列見出し「開始日」の位置を実際のシートに合わせて下さい(★印)
Option Explicit
Private Const cstrMaster As String = "Sheet1" '★出荷マスタのシート名(実際の名前に変更) Private Const clngColumns As Long = 18 '★出荷マスタの列数 Private Const cstrTop As String = "B2" '★出荷マスタの見出し先頭セル位置(「開始日」の位置)
Private rngList As Range 'マスタの列見出し先頭セル位置 Private rngWork As Range '作業用シートの抽出範囲 Private rngCrit As Range '作業用シートの条件範囲 Private lngRows As Long 'List行数(最終行位置) Private dicItemList As Object '商品IDをKeyとした品名List
Private Sub UserForm_Initialize()
Const cstTempNo As String = "Temporarily"
Dim vntData As Variant
'Listの先頭セル位置を基準とする(先頭列の列見出しのセル位置) Set rngList = Worksheets(cstrMaster).Range(cstrTop)
'抽出用シートの抽出範囲 Set rngWork = Worksheets("抽出").Range("A1:E1") rngWork.Item(1, 1).Value = cstTempNo
'抽出用シートの条件範囲 Set rngCrit = rngWork.Parent.Range("G1:G2")
With rngList '行数の取得 lngRows = .Offset(Rows.Count - .Row).End(xlUp).Row - .Row If lngRows <= 0 Then lngRows = 0 Else '最終列の後ろに仮のレコード番号を入力 .Offset(, clngColumns).Value = cstTempNo .Offset(1, clngColumns).Resize(lngRows).Formula = "=Row()-" & .Row End If End With
'「指示No」を無重複で取得 vntData = GetNumb If Not VarType(vntData) = vbBoolean Then ComboBox1.List = vntData End If
ComboBox2.ColumnCount = 2
'Dictionaryオブジェクトを取得 Set dicItemList = CreateObject("Scripting.Dictionary") 'Dictionaryに品名Listを取得 GetItemList
End Sub
Private Sub UserForm_Terminate()
'最終列の後ろに仮のレコード番号を破棄 rngList.Offset(, clngColumns).EntireColumn.ClearContents
Set dicItemList = Nothing Set rngList = Nothing Set rngWork = Nothing Set rngCrit = Nothing
End Sub
Private Sub ComboBox1_Enter()
'各コントロールをクリア ClearControls
End Sub
Private Sub ComboBox1_Exit(ByVal Cancel As MSForms.ReturnBoolean)
'指示No
Dim i As Long Dim vntData As Variant Dim lngRow As Long
If ComboBox1.ListIndex > -1 Then '商品IDのデータを取得 vntData = ExtractID(ComboBox1.Text, lngRow) With ComboBox2 '抽出行数が0で無いなら If lngRow > 0 Then 'ComboBox2にListを設定 .List = vntData .ListIndex = 0 Else 'ComboBox2と各コントロールをクリア .Clear ClearControls End If End With Else 'Dictionaryから商品IDと品名を取り出しComboBox2に設定 vntData = dicItemList.Keys With ComboBox2 .Clear For i = 0 To UBound(vntData) .AddItem vntData(i) .List(.ListCount - 1, 1) = dicItemList(vntData(i)) Next i End With End If
End Sub
Private Sub ComboBox2_Click()
'商品ID
If ComboBox1.ListIndex > -1 Then With ComboBox2 If .ListIndex > -1 Then '各コントロールにデータ読み込み GetLitData rngWork.Cells(2, 1).Offset(.ListIndex).Value End If End With End If
End Sub
Private Sub ComboBox2_Exit(ByVal Cancel As MSForms.ReturnBoolean)
With ComboBox2 '商品IDの選択が無い場合 If .ListIndex = -1 Then 'TextBox部に入力が在る場合 If .Text <> "" Then '商品IDListを探し在ったら If dicItemList.Exists(.Text) Then 'TextBox6に品名を代入 TextBox6.Text = dicItemList.Item(.Text) Else TextBox6.Text = "" End If Else TextBox6.Text = "" End If Else TextBox6.Text = .List(.ListIndex, 1) End If End With
End Sub
Private Sub CommandButton1_Click()
'更新/追加
Dim lngRow As Long Dim vntData As Variant Dim lngIndex As Long Dim lngButtons As Long Dim strPrompt As String
'商品IDの選択位置を取得 lngIndex = ComboBox2.ListIndex
'指示Noが選ばれている場合 If ComboBox1.ListIndex > -1 Then '商品IDが選択されている場合 If lngIndex > -1 Then '「指示数量」に「*」が入力されていなかったら If StrComp(Trim(TextBox7.Text), "*", vbTextCompare) <> 0 Then strPrompt = "レコードを更新します" If MsgBox(strPrompt, vbQuestion + vbYesNo) = vbYes Then '既存のレコードを更新 PutLitData rngWork.Cells(2, 1).Offset(lngIndex).Value End If Else strPrompt = "レコードを追加します" If StrComp(rngWork.Cells(2, 5).Offset(lngIndex).Value, "*", vbTextCompare) = 0 Then strPrompt = strPrompt & vbLf & "はい:レコード追加" _ & vbLf & "いいえ:レコード更新" lngButtons = vbQuestion + vbYesNoCancel Else lngButtons = vbQuestion + vbYesNo End If Select Case MsgBox(strPrompt, lngButtons) Case vbNo '既存のレコードを更新 lngRow = rngWork.Cells(2, 1).Offset(lngIndex).Value PutLitData lngRow Case vbYes 'レコードを追加 lngRow = rngWork.Cells(2, 1).Offset(lngIndex).Value + 1 rngList.Offset(lngRow).EntireRow.Insert PutLitData lngRow lngIndex = lngIndex + 1 lngRows = lngRows + 1 End Select End If Else 'TextBox部には入力が在る場合 If ComboBox2.Text <> "" Then strPrompt = "新規レコードを追加します" If MsgBox(strPrompt, vbQuestion + vbYesNo) = vbYes Then 'レコードを追加 lngIndex = ComboBox2.ListCount lngRow = rngWork.Cells(2, 1).Offset(lngIndex - 1).Value + 1 rngList.Offset(lngRow).EntireRow.Insert PutLitData lngRow lngRows = lngRows + 1 'Dictionaryに登録 dicItemList.Item(ComboBox2.Text) = TextBox6.Text End If End If End If Else '指示Noと商品IDに入力が在る場合 If ComboBox1.Text <> "" And ComboBox2.Text <> "" Then strPrompt = "List最終行に新規レコードを追加します" If MsgBox(strPrompt, vbQuestion + vbYesNo) = vbYes Then 'List最終行にレコードを追加 lngRows = lngRows + 1 lngIndex = 0 lngRow = lngRows If ComboBox2.ListIndex = -1 Then 'Dictionaryに登録 dicItemList.Item(ComboBox2.Text) = TextBox6.Text End If 'データを転記 PutLitData lngRow '「指示No」を無重複で取得 vntData = GetNumb If Not VarType(vntData) = vbBoolean Then ComboBox1.List = vntData End If End If End If End If
'商品IDのデータを取得 vntData = ExtractID(ComboBox1.Text, lngRow) With ComboBox2 '抽出行数が0で無いなら If lngRow > 0 Then 'ComboBox2にListを設定 .List = vntData 'ListIndexを再設定 .ListIndex = lngIndex End If End With
End Sub
Private Sub CommandButton2_Click()
'閉じる
Unload Me
End Sub
Private Sub DoFilter(rngScope As Range, _ rngCriteria As Range, _ rngCopyTo As Range, _ Optional blnUnique As Boolean)
' AdvancedFilterを実行
rngScope.AdvancedFilter _ Action:=xlFilterCopy, _ CriteriaRange:=rngCriteria, _ CopyToRange:=rngCopyTo, _ Unique:=blnUnique
End Sub
Private Function GetNumb() As Variant
Dim i As Long Dim lngRow As Long Dim vntData As Variant
'「指示No」を無重複で取得 DoFilter rngList.Cells(1, 2).Resize(lngRows + 1), _ rngCrit.Cells(1, 1).Offset(, 1), _ rngWork.Cells(1, 2), True
With rngWork.Cells(1, 2) '行数の取得 lngRow = .Offset(Rows.Count - .Row).End(xlUp).Row - .Row If lngRows > 0 Then vntData = .Offset(1).Resize(lngRow, 2).Value For i = 1 To lngRow vntData(i, 1) = CStr(vntData(i, 1)) Next i ReDim Preserve vntData(1 To lngRow, 1 To 1) GetNumb = vntData Else GetNumb = False End If End With
End Function
Private Sub GetItemList()
Dim i As Long Dim lngRow As Long Dim vntData As Variant
'「商品ID」「品名」を無重複で取得 DoFilter rngList.Cells(1, 7).Resize(lngRows + 1, 2), _ rngCrit.Cells(1, 1).Offset(, 1), _ rngWork.Cells(1, 3).Resize(, 2), True
With rngWork.Cells(1, 3) '行数の取得 lngRow = .Offset(Rows.Count - .Row).End(xlUp).Row - .Row If lngRows > 0 Then vntData = .Offset(1).Resize(lngRow, 2).Value 'Dictionaryに商品IDをKeyとして品名を登録 For i = 1 To lngRow dicItemList.Item(CStr(vntData(i, 1))) = vntData(i, 2) Next i End If End With
End Sub
Private Function ExtractID(vntCrit As Variant, lngRow As Long) As Variant
Dim i As Long Dim vntData As Variant
'条件範囲にComboBoxの値を代入(式の形で) rngCrit.Cells(2, 1).Value = "=""" & vntCrit & """"
'AdvancedFilterを実行 DoFilter rngList.Resize(lngRows + 1, clngColumns + 1), rngCrit, rngWork
'抽出範囲から With rngWork.Cells(1, 1) '抽出行数を取得 lngRow = .Offset(Rows.Count - .Row).End(xlUp).Row - .Row '列見出し以上の行が在るなら If lngRow > 0 Then 'データを配列に取得 vntData = .Offset(1, 2).Resize(lngRow, 2).Value '「商品ID」を文字列に変換 For i = 1 To lngRow vntData(i, 1) = CStr(vntData(i, 1)) Next i '戻り値として「商品ID」「品名」を配列で返す ExtractID = vntData End If End With
End Function
Private Sub ClearControls()
TextBox1.Text = "" '開始日 TextBox2.Text = "" '部署1 TextBox3.Text = "" '部署2 TextBox4.Text = "" '部署3 TextBox5.Text = "" '担当 ComboBox2.Text = "" '商品ID TextBox6.Text = "" '品名 TextBox7.Text = "" '指示数量 TextBox8.Text = "" '完成数量 TextBox9.Text = "" '完了日 TextBox10.Text = "" '出荷日 TextBox11.Text = "" '出荷先 TextBox12.Text = "" '出荷数
End Sub
Private Sub GetLitData(lngRow As Long)
'出荷マスタ指定位置因り With rngList TextBox1.Text = .Offset(lngRow, 0).Value '開始日 'ComboBox1.Text = .Offset(lngRow, 1).Value '指示No 使わない TextBox2.Text = .Offset(lngRow, 2).Value '部署1 TextBox3.Text = .Offset(lngRow, 3).Value '部署2 TextBox4.Text = .Offset(lngRow, 4).Value '部署3 TextBox5.Text = .Offset(lngRow, 5).Value '担当 'ComboBox2.Text = .Offset(lngRow, 6).Value '商品ID 使わない TextBox6.Text = .Offset(lngRow, 7).Value '品名 TextBox7.Text = .Offset(lngRow, 8).Value '指示数量 TextBox8.Text = .Offset(lngRow, 9).Value '完成数量 TextBox9.Text = .Offset(lngRow, 14).Value '完了日 TextBox10.Text = .Offset(lngRow, 15).Value '出荷日 TextBox11.Text = .Offset(lngRow, 16).Value '出荷先 TextBox12.Text = .Offset(lngRow, 17).Value '出荷数 End With
End Sub
Private Sub PutLitData(lngRow As Long)
'入荷マスタを更新 With rngList .Offset(lngRow, 0).Value = TextBox1.Text '開始日 .Offset(lngRow, 1).Value = ComboBox1.Text '指示No .Offset(lngRow, 2).Value = TextBox2.Text '部署1 .Offset(lngRow, 3).Value = TextBox3.Text '部署2 .Offset(lngRow, 4).Value = TextBox4.Text '部署3 .Offset(lngRow, 5).Value = TextBox5.Text '担当 .Offset(lngRow, 6).Value = ComboBox2.Text '商品ID .Offset(lngRow, 7).Value = TextBox6.Text '品名 .Offset(lngRow, 8).Value = TextBox7.Text '指示数量 .Offset(lngRow, 9).Value = TextBox8.Text '完成数量 .Offset(lngRow, 14).Value = TextBox9.Text '完了日 .Offset(lngRow, 15).Value = TextBox10.Text '出荷日 .Offset(lngRow, 16).Value = TextBox11.Text '出荷先 .Offset(lngRow, 17).Value = TextBox12.Text '出荷数 .Offset(lngRow, clngColumns).Formula _ = "=Row()-" & rngList.Row '仮番号 End With
End Sub
尚、操作する出荷シートのT列をUserFormが開いている間は、作業列として使い 仮の行番号を数式で入れる状態と成ります、またUserFormが閉じられる時にこの列は消去されます 操作は、UserFormを表示して、「指示No」のComboBox1に指示Noを入力するか、プルダウンで選択して下さい ComboBox1からフォーカスが移ると、出荷シートから指定の指示Noを抽出して、抽出したレコードの 商品IDがComboBox2のListに設定されますので、Listから選択されたレコードがUserFormのコントロールに表示されます
表示されたら、各コントロールの値を修正し更新/追加ボタンを押します この時、「指示数量」に「*」だけが入った場合、現在ComboBox2で選択されたレコードを更新するか、 表示されているデータで新規レコードを追加するか、キャンセルをするかを聞いて来ますので、此れに答えます 「はい」を選択すると、現在ComboBox2で選択されたレコードの下に新規レコードが追加されます 「いいえ」を選択すると、現在ComboBox2で選択されたレコードが更新されます 「キャンセル」の場合、何も行いません また、「指示数量」に「*」以外が入った場合は、レコードの更新だけが行われます 尚、「指示No」のComboBox1に出荷シート無い指示Noを入力し、商品IDも入力されていれば 出荷シートの最終行の下に、ComboBox1の番号の新規レコードが作成されます
(Bun)
Bunさま
ありがとうございます。 試してみたところほぼ希望通りにできました。
申し訳ありません、追加なんですが…
・上に書いたのですが、 > あと、リストボックスに表示する時に商品IDと商品名だけでは特定できないかもしれないので「開始日」または「指示数量」まで表示したいです。 これは今ComboBox2に商品名が表示されて選ぶようにとのことですが、できればキーとして 「商品名」 「部署3」 「指示数量」 で特定したいです(すみません、開始日ではなく部署に変えました)
・レコードの更新と追加ですが、 >この時、「指示数量」に「*」だけが入った場合、現在ComboBox2で選択されたレコードを更新するか、 >表示されているデータで新規レコードを追加するか、キャンセルをするかを聞いて来ますので、此れに答えます レコード追加の際に「指示数量」に必ず「*」が入るとは限らないケースも有り得るので、できればコマンドボタンを2個用意するか オプションボタンなどの選択で「更新」か「追加」かを選びたいです。 (人の入力ミスで「指示数量」を「*」に変更するのを忘れたまま登録→OKすることも考えられるので)
・あとこれはこちらで変更しただけですが、「出荷先」を顧客マスターシートから選択するために「ComboBox3」に変更しました。 (プルダウンから選ぶコードはできたのでコントロールの変更だけです)
何か色々欲を言って申し訳ありません
(ふーさん)
すみません、もう一つ追加です。
データを「追加」する際に、元のデータのL列〜O列の部分をコピーして挿入したいです。 (N列には計算式が入っています)
(ふーさん)
横から失礼。 コードを書いていたら、すでにBunさんから(同じような方法での)コードがアップされたので、 こちらのアップは控えます。
1点のみ。入力項目はテキストボックスを使うわけだけど、(さわってほしくない)表示項目はラベルにしたほうが無難。 (というか、ラベルにすべきだと)
(ぶらっと)
>・上に書いたのですが、 >> あと、リストボックスに表示する時に商品IDと商品名だけでは特定できないかもしれないので「開始日」または「指示数量」まで表示したいです。 >これは今ComboBox2に商品名が表示されて選ぶようにとのことですが、できればキーとして >「商品名」 >「部署3」 >「指示数量」 >で特定したいです(すみません、開始日ではなく部署に変えました)
此れ、使い方を勘違いして居ませんか? 上記の項目をKeyとしてどうやって使うの? 現状のコードでは先ず、「指示No」のComboBox1に手入力若しくは、List選択してフォーカスが移れば(Enterすれば)、 出荷シートから選択された「指示No」に該当するレコードの位置と商品ID、品名等が抽出され その、抽出された商品IDのListがComboBox2のListに設定され、先頭の商品IDが自動的に選択されます と同時に、選択されたレコードの値が各コントロールに表示されます 次に、フォーカスをComboBox2に移し、↓↑Keyを押せば次々にレコードの値が各コントロールに表示されます 因って、「商品名」も「部署3」も「指示数量」も全て確認出来る筈ですので、態々キーを設定して云々は必要無いと思いますが?
>レコード追加の際に「指示数量」に必ず「*」が入るとは限らないケースも有り得るので、できればコマンドボタンを2個用意するか >オプションボタンなどの選択で「更新」か「追加」かを選びたいです。
>データを「追加」する際に、元のデータのL列〜O列の部分をコピーして挿入したいです。 >(N列には計算式が入っています)
此れに就いては、最後に変更したコードをUpします 尚、新規データの入力は行わない様ですが「L列〜O列の部分をコピーする」を行うので、 Listにデータの無い状態で新規データの入力を行うとL列〜O列に列見出しがCopyされるので注意して下さい
また、今回のコードでは、商品マスタ(商品IDと品名の対比表)が在るのかが解らないので 出荷データの中の商品IDと品名を全てUserFormの立ち上げ時に読み込んで持っていますので レコード追加等でComboBox2のListに無い商品IDをComboBox2に手打ちすれば、出荷データに在る商品IDなら 品名が表示される様に成っています もし、商品マスタ(商品IDと品名の対比表)が在るならそちらを持たせる様に変更した方が善いと思います
ぶらっとさんの
>1点のみ。入力項目はテキストボックスを使うわけだけど、(さわってほしくない)表示項目はラベルにしたほうが無難。 >(というか、ラベルにすべきだと)
ご忠告ごもっともだと思いますが? 上司と言う物は気まぐれな物で、いつ何時に入力や修正をUserFormでやれと言う事に成るかも解りませんので TextBox、ComboBoxで作って置いて、使わない(弄られたくない)コントロールは「Locked プロパティ」を Trueにして置けば編集出来なくなりますの、デザイン画面で此れを設定すれば善いと思います
コードの変更点をUpします コントロールは、CommandButton3を追加して置きます 以下のプロシージャを差し替えて下さい
Private Sub CommandButton1_Click()
'更新
Dim lngRow As Long Dim vntData As Variant Dim lngIndex As Long Dim strPrompt As String
'商品IDの選択位置を取得 lngIndex = ComboBox2.ListIndex
'指示Noが選ばれている場合 If ComboBox1.ListIndex > -1 Then '商品IDが選択されている場合 If lngIndex > -1 Then strPrompt = "レコードを更新します" If MsgBox(strPrompt, vbQuestion + vbYesNo) = vbYes Then '既存のレコードを更新 lngRow = rngWork.Cells(2, 1).Offset(lngIndex).Value PutLitData lngRow, False End If End If End If
'商品IDのデータを取得 vntData = ExtractID(ComboBox1.Text, lngRow) With ComboBox2 '抽出行数が0で無いなら If lngRow > 0 Then 'ComboBox2にListを設定 .List = vntData 'ListIndexを再設定 .ListIndex = lngIndex End If End With
End Sub
Private Sub CommandButton3_Click()
'追加
Dim lngRow As Long Dim vntData As Variant Dim lngIndex As Long Dim strPrompt As String
'商品IDの選択位置を取得 lngIndex = ComboBox2.ListIndex
'指示Noが選ばれている場合 If ComboBox1.ListIndex > -1 Then strPrompt = "新規レコードを追加します" '商品IDが選択されている場合 If lngIndex > -1 Then If MsgBox(strPrompt, vbQuestion + vbYesNo) = vbYes Then 'レコードを追加 lngRow = rngWork.Cells(2, 1).Offset(lngIndex).Value + 1 rngList.Offset(lngRow).EntireRow.Insert PutLitData lngRow, True lngIndex = lngIndex + 1 lngRows = lngRows + 1 End If Else 'TextBox部には入力が在る場合 If ComboBox2.Text <> "" Then If MsgBox(strPrompt, vbQuestion + vbYesNo) = vbYes Then 'レコードを追加 lngIndex = ComboBox2.ListCount lngRow = rngWork.Cells(2, 1).Offset(lngIndex - 1).Value + 1 rngList.Offset(lngRow).EntireRow.Insert PutLitData lngRow, True lngRows = lngRows + 1 'Dictionaryに登録 dicItemList.Item(ComboBox2.Text) = TextBox6.Text End If End If End If Else '指示Noと商品IDに入力が在る場合 If ComboBox1.Text <> "" And ComboBox2.Text <> "" Then strPrompt = "List最終行に新規レコードを追加します" If MsgBox(strPrompt, vbQuestion + vbYesNo) = vbYes Then 'List最終行にレコードを追加 lngRows = lngRows + 1 lngIndex = 0 lngRow = lngRows If ComboBox2.ListIndex = -1 Then 'Dictionaryに登録 dicItemList.Item(ComboBox2.Text) = TextBox6.Text End If 'データを転記 PutLitData lngRow, True '「指示No」を無重複で取得 vntData = GetNumb If Not VarType(vntData) = vbBoolean Then ComboBox1.List = vntData End If End If Else Exit Sub End If End If
'商品IDのデータを取得 vntData = ExtractID(ComboBox1.Text, lngRow) With ComboBox2 '抽出行数が0で無いなら If lngRow > 0 Then 'ComboBox2にListを設定 .List = vntData 'ListIndexを再設定 .ListIndex = lngIndex End If End With
End Sub
Private Sub PutLitData(lngRow As Long, blnNewLine As Boolean)
'入荷マスタを更新 With rngList .Offset(lngRow, 0).Value = TextBox1.Text '開始日 .Offset(lngRow, 1).Value = ComboBox1.Text '指示No .Offset(lngRow, 2).Value = TextBox2.Text '部署1 .Offset(lngRow, 3).Value = TextBox3.Text '部署2 .Offset(lngRow, 4).Value = TextBox4.Text '部署3 .Offset(lngRow, 5).Value = TextBox5.Text '担当 .Offset(lngRow, 6).Value = ComboBox2.Text '商品ID .Offset(lngRow, 7).Value = TextBox6.Text '品名 .Offset(lngRow, 8).Value = TextBox7.Text '指示数量 .Offset(lngRow, 9).Value = TextBox8.Text '完成数量 .Offset(lngRow, 14).Value = TextBox9.Text '完了日 .Offset(lngRow, 15).Value = TextBox10.Text '出荷日 '.Offset(lngRow, 16).Value = TextBox11.Text '出荷先 .Offset(lngRow, 16).Value = ComboBox3.Text '出荷先 .Offset(lngRow, 17).Value = TextBox12.Text '出荷数 '追加の場合 If blnNewLine Then .Offset(lngRow, clngColumns).Formula _ = "=Row()-" & rngList.Row '仮番号 '転記元レコードからL列〜O列をCopy .Offset(lngRow - 1, 10).Resize(, 4).Copy _ Destination:=.Offset(lngRow, 10) End If End With
End Sub
(Bun)
>これは今ComboBox2に商品名が表示されて選ぶようにとのことですが、できればキーとして >「商品名」 >「部署3」 >「指示数量」 >で特定したいです(すみません、開始日ではなく部署に変えました)
上記に就いて、今朝思いついたのですが?、考え方を代えてコードを作り直しました
先ず「抽出」シートのレイアウトを変更します 「抽出」シートを以下に
A B C D E F G H 1 指示No 商品ID 品名 指示数量 部署3 指示No
B1 :「指示No」、C1:「商品ID」、D1:「品名」、E1:「指示数量」、F1:「部署3」H1:「指示No」とします 「出荷したか」を記入しているシートから列見出しをCopyして下さい
次にUserFormを用意します 各コントロールの配置は以下の様にします 指示No :ComboBox1 開始日 :TextBox1 部署1 :TextBox2 部署2 :TextBox3 部署3 :TextBox4 担当 :TextBox5 商品ID :ComboBox2 品名 :TextBox6 指示数量 :TextBox7 完成数量 :TextBox8 完了日 :TextBox9 出荷日 :TextBox10 出荷先 :ComboBox3 出荷数 :TextBox12 更新:CommandButton1 閉じる:CommandButton2 追加:CommandButton3
此処にComboBox4:行選択を追加します、尚、ComboBox3は商品IDの選択だけの機能にします(ComboBox2と同じ) ComboBox4は複数列のComboで「商品ID」「品名」「部署3」「指示数量」と仮番号を表示し このComboの値に因り、指定した「指示No」の行選択を行います (コントロールを追加するのでタブオーダーの変更に注意して下さい)
以下をUserFormのコードモジュールに記述して下さい
Option Explicit
Private Const cstrMaster As String = "Sheet1" '★出荷マスタのシート名(実際の名前に変更) Private Const clngColumns As Long = 18 '★出荷マスタの列数 Private Const cstrTop As String = "B2" '★出荷マスタの見出し先頭セル位置(「開始日」の位置)
Private rngList As Range 'マスタの列見出し先頭セル位置 Private rngWork As Range '作業用シートの抽出範囲 Private rngCrit As Range '作業用シートの条件範囲 Private lngRows As Long 'List行数(最終行位置)
Private Sub UserForm_Initialize()
Const cstTempNo As String = "Temporarily"
Dim vntData As Variant
'Listの先頭セル位置を基準とする(先頭列の列見出しのセル位置) Set rngList = Worksheets(cstrMaster).Range(cstrTop) rngList.Parent.Activate
'抽出用シートの抽出範囲 Set rngWork = Worksheets("抽出").Range("A1:G1") rngWork.Item(1, 1).Value = cstTempNo
'抽出用シートの条件範囲 Set rngCrit = rngWork.Parent.Range("H1:H2")
With rngList '行数の取得 lngRows = .Offset(Rows.Count - .Row).End(xlUp).Row - .Row If lngRows <= 0 Then lngRows = 0 Else '最終列の後ろに仮のレコード番号を入力 .Offset(, clngColumns).Value = cstTempNo .Offset(1, clngColumns).Resize(lngRows).Formula = "=Row()-" & .Row End If End With
'「指示No」を無重複で取得 vntData = GetNumb If Not VarType(vntData) = vbBoolean Then ComboBox1.List = vntData End If
'商品IDと品名を登録 ComboBox2.ColumnCount = 2 GetItemList ComboBox2
'行選択用ComboBoxの設定 With ComboBox4 .ColumnCount = 6 .ColumnWidths = "72;0;72;72;72;72" End With
End Sub
Private Sub UserForm_Terminate()
'最終列の後ろに仮のレコード番号を破棄 rngList.Offset(, clngColumns).EntireColumn.ClearContents rngList.Activate
Set rngList = Nothing Set rngWork = Nothing Set rngCrit = Nothing
End Sub
Private Sub ComboBox1_Enter()
ComboBox4.ListIndex = -1 '各コントロールをクリア ClearControls
End Sub
Private Sub ComboBox1_Click()
'指示No
Dim i As Long Dim vntData As Variant Dim lngRow As Long
If ComboBox1.ListIndex > -1 Then '行選択のデータを取得 vntData = ExtractID(ComboBox1.Text, lngRow) With ComboBox4 '抽出行数が0で無いなら If lngRow > 0 Then 'ComboBox4にListを設定 .List = vntData .ListIndex = 0 Else 'ComboBox4と各コントロールをクリア .Clear ClearControls End If End With End If
End Sub
Private Sub ComboBox2_Click()
'商品ID
With ComboBox2 If .ListIndex > -1 Then TextBox6.Text = .List(.ListIndex, 1) Else TextBox6.Text = "" End If End With
End Sub
Private Sub ComboBox4_Change()
If ComboBox1.ListIndex > -1 Then With ComboBox4 If .ListIndex > -1 Then '各コントロールにデータ読み込み GetLitData rngWork.Cells(2, 1).Offset(.ListIndex).Value Else ClearControls End If End With End If
End Sub
Private Sub CommandButton1_Click()
'更新
Dim lngRow As Long Dim vntData As Variant Dim lngIndex As Long Dim strPrompt As String
'行選択の選択位置を取得 lngIndex = ComboBox4.ListIndex
'指示Noが選ばれている場合 If ComboBox1.ListIndex > -1 Then '商品IDが選択されている場合 If lngIndex > -1 Then strPrompt = "レコードを更新します" If MsgBox(strPrompt, vbQuestion + vbYesNo) = vbYes Then '既存のレコードを更新 lngRow = rngWork.Cells(2, 1).Offset(lngIndex).Value PutLitData lngRow, False End If End If End If
'行選択のデータを取得 vntData = ExtractID(ComboBox1.Text, lngRow) With ComboBox4 '抽出行数が0で無いなら If lngRow > 0 Then 'ComboBox2にListを設定 .List = vntData 'ListIndexを再設定 .ListIndex = lngIndex End If End With
End Sub
Private Sub CommandButton2_Click()
'閉じる
Unload Me
End Sub
Private Sub CommandButton3_Click()
'追加
Dim lngRow As Long Dim vntData As Variant Dim lngIndex As Long Dim strPrompt As String
'行選択の選択位置を取得 lngIndex = ComboBox4.ListIndex
'指示Noが選ばれている場合 If ComboBox1.ListIndex > -1 Then strPrompt = "新規レコードを追加します" '行選択が選択されている場合 If lngIndex > -1 Then If MsgBox(strPrompt, vbQuestion + vbYesNo) = vbYes Then 'レコードを追加 lngRow = rngWork.Cells(2, 1).Offset(lngIndex).Value + 1 rngList.Offset(lngRow).EntireRow.Insert PutLitData lngRow, True lngIndex = lngIndex + 1 lngRows = lngRows + 1 End If End If Else '指示Noと商品IDに入力が在る場合 If ComboBox1.Text <> "" Then strPrompt = "List最終行に新規レコードを追加します" If MsgBox(strPrompt, vbQuestion + vbYesNo) = vbYes Then 'List最終行にレコードを追加 lngRows = lngRows + 1 lngIndex = 0 lngRow = lngRows 'データを転記 PutLitData lngRow, True '「指示No」を無重複で取得 vntData = GetNumb If Not VarType(vntData) = vbBoolean Then ComboBox1.List = vntData End If End If Else Exit Sub End If End If
'商品IDのデータを取得 vntData = ExtractID(ComboBox1.Text, lngRow) With ComboBox4 '抽出行数が0で無いなら If lngRow > 0 Then 'ComboBox2にListを設定 .List = vntData 'ListIndexを再設定 .ListIndex = lngIndex End If End With
End Sub
Private Sub DoFilter(rngScope As Range, _ rngCriteria As Range, _ rngCopyTo As Range, _ Optional blnUnique As Boolean)
' AdvancedFilterを実行
rngScope.AdvancedFilter _ Action:=xlFilterCopy, _ CriteriaRange:=rngCriteria, _ CopyToRange:=rngCopyTo, _ Unique:=blnUnique
End Sub
Private Function GetNumb() As Variant
Dim i As Long Dim lngRow As Long Dim vntData As Variant
'「指示No」を無重複で取得 DoFilter rngList.Cells(1, 2).Resize(lngRows + 1), _ rngCrit.Cells(1, 1).Offset(, 1), _ rngWork.Cells(1, 2), True
With rngWork.Cells(1, 2) '行数の取得 lngRow = .Offset(Rows.Count - .Row).End(xlUp).Row - .Row If lngRows > 0 Then vntData = .Offset(1).Resize(lngRow, 2).Value For i = 1 To lngRow vntData(i, 1) = CStr(vntData(i, 1)) Next i ReDim Preserve vntData(1 To lngRow, 1 To 1) GetNumb = vntData Else GetNumb = False End If End With
End Function
Private Sub GetItemList(cboItems As MSForms.ComboBox)
Dim i As Long Dim j As Long Dim lngRow As Long Dim vntData As Variant
'「商品ID」「品名」を無重複で取得 DoFilter rngList.Cells(1, 7).Resize(lngRows + 1, 2), _ rngCrit.Cells(1, 1).Offset(, 1), _ rngWork.Cells(1, 3).Resize(, 2), True
With rngWork.Cells(1, 3) '行数の取得 lngRow = .Offset(Rows.Count - .Row).End(xlUp).Row - .Row If lngRows <= 0 Then Exit Sub End If '商品IDと品名を取得 vntData = .Offset(1).Resize(lngRow, 2).Value End With
'ComboBoxに商品ID昇順に品名を登録 With cboItems For i = 1 To lngRow For j = 0 To .ListCount - 1 If .List(j, 0) > CStr(vntData(i, 1)) Then Exit For End If Next j If j = .ListCount - 1 Then .AddItem CStr(vntData(i, 1)), j .List(j, 1) = vntData(i, 2) Else .AddItem CStr(vntData(i, 1)) .List(.ListCount - 1, 1) = vntData(i, 2) End If Next i End With
End Sub
Private Function ExtractID(vntCrit As Variant, lngRow As Long) As Variant
Dim i As Long Dim vntData As Variant
'条件範囲にComboBoxの値を代入(式の形で) rngCrit.Cells(2, 1).Value = "=""" & vntCrit & """"
'AdvancedFilterを実行 DoFilter rngList.Resize(lngRows + 1, clngColumns + 1), rngCrit, rngWork
'抽出範囲から With rngWork.Cells(1, 1) '抽出行数を取得 lngRow = .Offset(Rows.Count - .Row).End(xlUp).Row - .Row '列見出し以上の行が在るなら If lngRow > 0 Then 'データを配列に取得 vntData = .Offset(1).Resize(lngRow, 6).Value '「仮番号」を文字列に変換 For i = 1 To lngRow vntData(i, 1) = CStr(vntData(i, 1)) Next i '戻り値として配列で返す ExtractID = vntData End If End With
End Function
Private Sub ClearControls()
TextBox1.Text = "" '開始日 TextBox2.Text = "" '部署1 TextBox3.Text = "" '部署2 TextBox4.Text = "" '部署3 TextBox5.Text = "" '担当 ComboBox2.Text = "" '商品ID TextBox6.Text = "" '品名 TextBox7.Text = "" '指示数量 TextBox8.Text = "" '完成数量 TextBox9.Text = "" '完了日 TextBox10.Text = "" '出荷日 'TextBox11.Text = "" '出荷先 ComboBox3.Text = "" '出荷先 TextBox12.Text = "" '出荷数
End Sub
Private Sub GetLitData(lngRow As Long)
'出荷マスタ指定位置因り With rngList TextBox1.Text = .Offset(lngRow, 0).Value '開始日 'ComboBox1.Text = .Offset(lngRow, 1).Value '指示No 使わない TextBox2.Text = .Offset(lngRow, 2).Value '部署1 TextBox3.Text = .Offset(lngRow, 3).Value '部署2 TextBox4.Text = .Offset(lngRow, 4).Value '部署3 TextBox5.Text = .Offset(lngRow, 5).Value '担当 ComboBox2.Text = .Offset(lngRow, 6).Value '商品ID TextBox6.Text = .Offset(lngRow, 7).Value '品名 TextBox7.Text = .Offset(lngRow, 8).Value '指示数量 TextBox8.Text = .Offset(lngRow, 9).Value '完成数量 TextBox9.Text = .Offset(lngRow, 14).Value '完了日 TextBox10.Text = .Offset(lngRow, 15).Value '出荷日 'TextBox11.Text = .Offset(lngRow, 16).Value '出荷先 ComboBox3.Text = .Offset(lngRow, 16).Value '出荷先 TextBox12.Text = .Offset(lngRow, 17).Value '出荷数 ComboBox4.Text = .Offset(lngRow, clngColumns).Value '★追加 仮番号 .Offset(lngRow).Resize(, clngColumns).Select '★追加 セル選択 End With
End Sub
Private Sub PutLitData(lngRow As Long, blnNewLine As Boolean)
'入荷マスタを更新 With rngList .Offset(lngRow, 0).Value = TextBox1.Text '開始日 .Offset(lngRow, 1).Value = ComboBox1.Text '指示No .Offset(lngRow, 2).Value = TextBox2.Text '部署1 .Offset(lngRow, 3).Value = TextBox3.Text '部署2 .Offset(lngRow, 4).Value = TextBox4.Text '部署3 .Offset(lngRow, 5).Value = TextBox5.Text '担当 .Offset(lngRow, 6).Value = ComboBox2.Text '商品ID .Offset(lngRow, 7).Value = TextBox6.Text '品名 .Offset(lngRow, 8).Value = TextBox7.Text '指示数量 .Offset(lngRow, 9).Value = TextBox8.Text '完成数量 .Offset(lngRow, 14).Value = TextBox9.Text '完了日 .Offset(lngRow, 15).Value = TextBox10.Text '出荷日 '.Offset(lngRow, 16).Value = TextBox11.Text '出荷先 .Offset(lngRow, 16).Value = ComboBox3.Text '出荷先 .Offset(lngRow, 17).Value = TextBox12.Text '出荷数 '追加の場合 If blnNewLine Then .Offset(lngRow, clngColumns).Formula _ = "=Row()-" & rngList.Row '仮番号 '転記元レコードからL列〜O列をCopy .Offset(lngRow - 1, 10).Resize(, 4).Copy _ Destination:=.Offset(lngRow, 10) End If End With
End Sub
(Bun)
ありがとうございます。
今試していたのですが、下記の現象についてお教えください。
あるデータを選択し、完了日などを記入してコマンドボタン1でデータを更新しました。 そのデータを元に、出荷先を変えたレコードをコマンドボタン3で行を挿入して追加しました。 しかし追加したデータに入力ミスがあったので、追加したデータを選択してコマンドボタン1でデータを更新しました
すると、L〜O列のデータが消えてしまいました…
更新・追加のどちらの場合にもL〜O列に値(計算式も含めて)をセットするような形にしておくべきでしょうか…
あとこちらでまた変更をしました。 TextBox4→ComboBox5にしました。
商品マスターはあります。 ただ、一つの商品IDに対して複数の名前が存在することがあります。 (クライアントが一つの商品IDで名前を変えて注文してくることがあるので)
(ふーさん)
>あるデータを選択し、完了日などを記入してコマンドボタン1でデータを更新しました。 >そのデータを元に、出荷先を変えたレコードをコマンドボタン3で行を挿入して追加しました。 >しかし追加したデータに入力ミスがあったので、追加したデータを選択してコマンドボタン1でデータを更新しました
>すると、L〜O列のデータが消えてしまいました… > >更新・追加のどちらの場合にもL〜O列に値(計算式も含めて)をセットするような形にしておくべきでしょうか…
成らないと思いますが? 更新なので、選択されているレコードが先頭の場合、直上のレコードの「指示No」が違っている場合が有ります この時、その違う「指示No」の「L〜O列に値(計算式も含めて)」をCopyしても善いのか?どうかに因ると思います?
もし、善いのなら以下をコメントアウトか削除すればCopyして来ますが?
Private Sub PutLitData(lngRow As Long, blnNewLine As Boolean)
'入荷マスタを更新 With rngList .Offset(lngRow, 0).Value = TextBox1.Text '開始日 .Offset(lngRow, 1).Value = ComboBox1.Text '指示No .Offset(lngRow, 2).Value = TextBox2.Text '部署1 .Offset(lngRow, 3).Value = TextBox3.Text '部署2 .Offset(lngRow, 4).Value = TextBox4.Text '部署3 .Offset(lngRow, 5).Value = TextBox5.Text '担当 .Offset(lngRow, 6).Value = ComboBox2.Text '商品ID .Offset(lngRow, 7).Value = TextBox6.Text '品名 .Offset(lngRow, 8).Value = TextBox7.Text '指示数量 .Offset(lngRow, 9).Value = TextBox8.Text '完成数量 .Offset(lngRow, 14).Value = TextBox9.Text '完了日 .Offset(lngRow, 15).Value = TextBox10.Text '出荷日 '.Offset(lngRow, 16).Value = TextBox11.Text '出荷先 .Offset(lngRow, 16).Value = ComboBox3.Text '出荷先 .Offset(lngRow, 17).Value = TextBox12.Text '出荷数 '追加の場合 ' If blnNewLine Then '★コメントアウト .Offset(lngRow, clngColumns).Formula _ = "=Row()-" & rngList.Row '仮番号 '転記元レコードからL列〜O列をCopy .Offset(lngRow - 1, 10).Resize(, 4).Copy _ Destination:=.Offset(lngRow, 10) ' End If '★コメントアウト End With
End Sub
>商品マスターはあります。 >ただ、一つの商品IDに対して複数の名前が存在することがあります。 >(クライアントが一つの商品IDで名前を変えて注文してくることがあるので)
此れは、運用の問題でComboBox2に表示する事は問題無いと思います ComboBox2は2列表示なので、商品IDを選ぶ際に、商品名も見て選べば善いと思います 尚、商品IDのマスタからの読み込みの場合、「Private Sub GetItemList」を書き換えなければ成りません
後、ComboBox2とComboBox4もそうですが? Upしたコードでは「ListWidth プロパティ」を設定した方が善かったのですが忘れていました 「Private Sub UserForm_Initialize()」の中の以下の部分(★印)を変更して下さい
'商品IDと品名を登録 GetItemList ComboBox2 '★変更 With ComboBox2 '★変更 .ColumnCount = 2 '★変更 .ListWidth = "144" '★変更 .ColumnWidths = "72;72" '★変更 End With
'行選択用ComboBoxの設定 With ComboBox4 .ColumnCount = 6 .ListWidth = "360" '★変更 .ColumnWidths = "72;0;72;72;72;72" End With
尚、「ListWidth プロパティ」の値と「.ColumnWidths」の値は実情に合わせて変更して下さい
(Bun)
書き忘れましたが? 此れ、最後にUpしたコード(マクロ)の方ですよね?
(Bun)
あれ、今試したら再発しませんでした…(L〜O列が消える) さっきは確かに消えていたのによく分かりません…
>此れ、最後にUpしたコード(マクロ)の方ですよね? はいそうです。
あと、以前のコードの
Private Sub ComboBox2_Exit(ByVal Cancel As MSForms.ReturnBoolean)
この部分は不要なのでしょうか。
(ふーさん)
>あれ、今試したら再発しませんでした…(L〜O列が消える) >さっきは確かに消えていたのによく分かりません…
コード的にはあり得ないと思いますが? 此方でのTestでは、この現象は出ていませんので?
>あと、以前のコードの > >Private Sub ComboBox2_Exit(ByVal Cancel As MSForms.ReturnBoolean) > >この部分は不要なのでしょうか。
最後のコードの方では、ComboBox2は商品IDの入力と、TextBox6の品名の入力だけを荷っているので 不必要です その代わり、以前のComboBox2の機能をComboBox4で行っています 因って、ComboBox4のタブオーダーをComboBox1(指示No)の次にしては方が使い善いよ思います?
(Bun)
ありがとうございます。
何度もすみません。
ComboBox1、ComboBox4以外でこちらで追加したコンボボックスですが、ユーザーフォームを表示した時点では プルダウンでリストの先頭にカーソルが来ているのですが、ComboBox1でデータを呼び出した後、ComboBox3やComboBox5を 見るとリストの最下行にカーソルが行ってしまいます。 コンボボックスのプロパティで、TabIndexは0にしています。 これは何故こうなるのかお教えいただけませんでしょうか?
(ふーさん)
>ComboBox1、ComboBox4以外でこちらで追加したコンボボックスですが、ユーザーフォームを表示した時点では >プルダウンでリストの先頭にカーソルが来ているのですが、ComboBox1でデータを呼び出した後、ComboBox3やComboBox5を >見るとリストの最下行にカーソルが行ってしまいます。
ComboBox3やComboBox5に対し何かコードを書いているなら(例えば、「Private Sub ComboBox3_Change()」の様な?) 其れにも因るので、其れを見なければ解りませんが? 書いて無いとすれば、常に!!最下行が選択される事は無いと思います? 何故なら、
Private Sub GetLitData(lngRow As Long)
'出荷マスタ指定位置因り With rngList TextBox1.Text = .Offset(lngRow, 0).Value '開始日 'ComboBox1.Text = .Offset(lngRow, 1).Value '指示No 使わない TextBox2.Text = .Offset(lngRow, 2).Value '部署1 TextBox3.Text = .Offset(lngRow, 3).Value '部署2 'TextBox4.Text = .Offset(lngRow, 4).Value '部署3 ComboBox5.Text = .Offset(lngRow, 4).Value '部署3 TextBox5.Text = .Offset(lngRow, 5).Value '担当 ComboBox2.Text = .Offset(lngRow, 6).Value '商品ID TextBox6.Text = .Offset(lngRow, 7).Value '品名 TextBox7.Text = .Offset(lngRow, 8).Value '指示数量 TextBox8.Text = .Offset(lngRow, 9).Value '完成数量 TextBox9.Text = .Offset(lngRow, 14).Value '完了日 TextBox10.Text = .Offset(lngRow, 15).Value '出荷日 'TextBox11.Text = .Offset(lngRow, 16).Value '出荷先 ComboBox3.Text = .Offset(lngRow, 16).Value '出荷先 TextBox12.Text = .Offset(lngRow, 17).Value '出荷数 ComboBox4.Text = .Offset(lngRow, clngColumns).Value '★追加 仮番号 .Offset(lngRow).Resize(, clngColumns).Select '★追加 セル選択 End With
End Sub
の所でComboBox3やComboBox5に値を代入していますので、ComboBox3やComboBox5のListに値が有れば 其の位置が選択されます
>コンボボックスのプロパティで、TabIndexは0にしています。 >これは何故こうなるのかお教えいただけませんでしょうか?
此れも何か変ですよ? TabIndexプロパティは、確か排他処理されると思いますので2つに0は入れられないと思います また、TabIndexを0にすれば、そのコントロールが最初にフォーカスを得る事に成り入力順を狂わせてしまうのでは? 尚、フォーカスを持たせない様にするならTabStopプロパティをFalseにします タブオーダーを変更するなら、直接TabIndexの値を変更しても善いのですが? VBEのデザイン画面で、変更するUserFormを選択して「表示」→「タブオーダー」でダイアログがでます 此処で、タブオーダーを変更した方が簡単だと思います(ダイアログに表示された上から順にフオーカスが当たる)
尚、今回のコードでは、タブオーダーがComboBox1が先頭、次にComboBox4とした方が使い勝手が善いと思います
(Bun)
ありがとうございます。
タブオーダーは順番通りにしました。
しかし、.ListIndex などを設定してもやはりコンボボックスの初期値がリストの最下行になります。 試しにコンボボックスのリストを取得しているマスターシートを、
見出し [空白] データ1 データ2 :
のように最初に空白セルを置いたらリストの一番上を参照するようになりました。
不思議なのはこのマスターシートは他のユーザーフォームでも参照しているのですが、そちらではこのような現象は起きないんです
でもとりあえず現象が解決したので助かりました。
ありがとうございました。
(ふーさん)
[ 一覧(最新更新順) ]
YukiWiki 1.6.7 Copyright (C) 2000,2001 by Hiroshi Yuki.
Modified by kazu.