Excel VBAのデータ参照方法について

このQ&Aのポイント
  • Excel VBAで別ブックからデータを参照する方法について苦戦しています。現在参考にしているサイトでは、ドロップダウンリストを作成し、そのドロップダウンリストの値に応じて別のセルにデータを表示する機能を実装するような内容が書かれています。しかし、コードの一部でエラーが発生しているようで、正しく動作しません。
  • 具体的には、セルA2からA10までにドロップダウンリストの入力規則を設定し、選択された値に応じてセルB2からB10にデータを表示するようにしたいと考えています。ただし、以下のコードを実行すると、エラーが発生してしまい、正常に動作しません。
  • 具体的なエラーは、セルB2の入力規則を設定する部分で発生しています。セルA2の値が空の場合には、セルB2の入力規則も削除するように指定していますが、その後の処理でエラーが発生してしまいます。改善策を教えてください。
回答を見る
  • ベストアンサー

入力規則のドロップダウンリストを連動

以下のサイトを参考に別ブックからデータを参照する方法で苦戦しています。 http://www.eurus.dti.ne.jp/yoneyama/Excel/vba/vba_validation.html Sub name_1()   Dim lCol As Long, lRow As Long   Dim i As Long, nName As String Dim Wb As Workbook ←追記 Set Wb = Workbooks("MyBook.xls") ←追記     On Error Resume Next     With Wb.Sheets("Sheet2")       lCol = .Range("A1").End(xlToRight).Column       ActiveWorkbook.Names("項目リスト").Delete       ActiveWorkbook.Names.Add Name:="項目リスト", _         RefersTo:=.Range(.Cells(1, 1), .Cells(1, lCol))       '----名前の定義       For i = 1 To lCol         lRow = .Cells(1, i).End(xlDown).Row         nName = .Cells(1, i).Value         ActiveWorkbook.Names(nName).Delete         .Range(.Cells(1, i), .Cells(lRow, i)).CreateNames Top:=True       Next i     End With End Sub Sub Macro2()   name_1   With Range("A2:A10").Validation     '--入力規則を削除     .Delete     '--入力規則を設定     .Add Type:=xlValidateList, _       Formula1:="=項目リスト"   End With   '--B2セルへ入力規則を設定   With Range("B2:B10").Validation     .Delete     .Add Type:=xlValidateList, _       Formula1:="=IF(A2="""",A2,INDIRECT(A2))"   End With End Sub Private Sub Worksheet_Change(ByVal Target As Range)   Dim c As Range Dim Wb As Workbook ←追記 Set Wb = Workbooks("MyBook.xls") ←追記     If Not (Application.Intersect(Target, Range("A2:B10")) Is Nothing) Then     name_1     Application.EnableEvents = False       If Target.Column = 1 Then         If Target.Value = "" Then           Target.Offset(0, 1).Value = ""         Else           Set c = Wb.Sheets("Sheet2").Range(Target.Value).Find(Target.Offset(0, 1).Value, lookat:=xlWhole) ←ここでエラー           If c Is Nothing Then             Target.Offset(0, 1).Value = ""           End If         End If       End If       If Target.Column = 2 Then         If Target.Value = "" Then           Target.Offset(0, -1).Value = ""         End If       End If     Application.EnableEvents = True     End If End Sub どのように改変すれば良いのでしょうか?

質問者が選んだベストアンサー

  • ベストアンサー
  • HohoPapa
  • ベストアンサー率65% (454/691)
回答No.5

>まさに、 > 入力規則を設定するブックが開くときに > マクロで候補群の埋まったブックも開き >必要なセル範囲の候補群たちを >元ブック側に定義する > という方法を取っています。 ありゃ、ごめんなさい。 既に解決しているようですが 私のコードを紹介させていただきます。 候補群を配列変数に保持するやり方です。 よかったら参考にしてください。 '以下ThisWorkbookモジュール Private Sub Workbook_Open()  GetMyList End Sub '以下、シートモジュール Private Sub Worksheet_Change(ByVal Target As Range)  SetMyList Target End Sub '以下、標準モジュール '//------------------------------------- '// 定数、変数 '//-------------------------------------  Const Listbook = "C:\OKWave\コンボボックス制御\候補群.xlsx"  Const MaxRows = 7   'メインの想定最大候補数  Const Maxcols = 10  'サブの想定最大候補数  Const MCombRow = 2  'メインの候補群セットセルの行位置  Const MCombCol = 2  'メインの候補群セットセルの列位置  Const SCombRow = 2  'サブの候補群セットセルの行位置  Const SCombCol = 3  'サブの候補群セットセルの列位置  Dim MyLists(MaxRows, Maxcols) As String '候補群格納変数     '//------------------------------------- '// 候補群ブックから一覧を取得して、 '//  二次配列に格納し、主コンボボックスに候補群をセット '//------------------------------------- Sub GetMyList()  Dim wb As Workbook  Dim RowCounter As Long  Dim ColCounter As Long  Dim wkList As String  Dim tgRange As Range    '候補群格納ブックが開いていたらいったん閉じる  For Each wb In Workbooks   If wb.FullName = Listbook Then    wb.Close   End If  Next wb    Set wb = Workbooks.Open(Listbook)  Erase MyLists    With wb.Sheets(1)   For RowCounter = 1 To MaxRows    For ColCounter = 1 To Maxcols     MyLists(RowCounter - 1, ColCounter) = _      .Cells(RowCounter, ColCounter).Value    Next ColCounter   Next RowCounter  End With  ColCounter = 1  wkList = ""  Do   If MyLists(0, ColCounter) = "" Then Exit Do   wkList = wkList & MyLists(0, ColCounter) & ","   ColCounter = ColCounter + 1  Loop  If wkList = "" Then Exit Sub  wkList = Left(wkList, Len(wkList) - 1)     With ThisWorkbook.Sheets(1)   Set tgRange = .Cells(MCombRow, MCombCol)  End With  ChgValidation tgRange, wkList  wb.Close   End Sub '//------------------------------------- '// 副コンボボックスに候補群をセット '//------------------------------------- Sub SetMyList(ByVal Target As Range)  Dim ColCounter As Long  Dim RowCounter As Long  Dim ColNum As Long  Dim wkList As String  Dim tgRange As Range    If ((Target.Row <> MCombRow) Or (Target.Column <> MCombCol)) Then Exit Sub  With ThisWorkbook.Sheets(1)   .Cells(SCombRow, SCombCol).Value = ""  End With  ColNum = 0    For ColCounter = 1 To Maxcols   If Target.Value = MyLists(0, ColCounter) Then    ColNum = ColCounter    Exit For   End If  Next ColCounter    RowCounter = 1  wkList = ""  Do   If MyLists(RowCounter, ColNum) = "" Then Exit Do   wkList = wkList & MyLists(RowCounter, ColNum) & ","   RowCounter = RowCounter + 1  Loop  If wkList = "" Then Exit Sub  wkList = Left(wkList, Len(wkList) - 1)    With ThisWorkbook.Sheets(1)   Set tgRange = .Cells(SCombRow, SCombCol)  End With    ChgValidation tgRange, wkList End Sub '//------------------------------------- '// 入力規則の設定、候補群セット関数 '//------------------------------------- Sub ChgValidation(MyRange As Range, SelText As String)  With MyRange   .Validation.Delete   .Validation.Add Type:=xlValidateList, AlertStyle:=xlValidAlertStop, Operator:= _     xlBetween, Formula1:=SelText   .Validation.IgnoreBlank = True   .Validation.InCellDropdown = True   .Validation.InputTitle = ""   .Validation.ErrorTitle = ""   .Validation.InputMessage = ""   .Validation.ErrorMessage = ""   .Validation.IMEMode = xlIMEModeNoControl   .Validation.ShowInput = True   .Validation.ShowError = True  End With End Sub

ampm2007
質問者

お礼

新たな方法をご提示頂き、有難うございました。

その他の回答 (5)

  • HohoPapa
  • ベストアンサー率65% (454/691)
回答No.6

さきほどポストした補足です。 画像を添付漏れしたので上げます。 また、範囲名を使っているのではなく 候補群の値を直接、入力候補群設定フィールドに 埋めています。

  • watabe007
  • ベストアンサー率62% (476/760)
回答No.4

こちらのテストではエラーなく動いています。 Sub Macro2()の内容は見ていませんので Sub name_1()   Dim lCol As Long, lRow As Long   Dim i As Long, nName As String   Dim Wb As Workbook   Set Wb = Workbooks("MyBook.xls")   On Error Resume Next   With Wb.Sheets("Sheet2")     lCol = .Range("A1").End(xlToRight).Column     Wb.Names("項目リスト").Delete     Wb.Names.Add Name:="項目リスト", _       RefersTo:=.Range(.Cells(1, 1), .Cells(1, lCol))     '----名前の定義     For i = 1 To lCol       lRow = .Cells(1, i).End(xlDown).Row       nName = .Cells(1, i).Value       Wb.Names(nName).Delete       .Range(.Cells(1, i), .Cells(lRow, i)). _         CreateNames Top:=True     Next i   End With End Sub '↓ If c Is Nothing Then の場合の処理だけで、見つかった場合は処理は無し? Private Sub Worksheet_Change(ByVal Target As Range)   Dim c As Range   Dim Wb As Workbook   Set Wb = Workbooks("MyBook.xls")   If Not (Application.Intersect(Target, Range("A2:B10")) Is Nothing) Then     name_1     Application.EnableEvents = False     If Target.Column = 1 Then       If Target.Value = "" Then         Target.Offset(0, 1).Value = ""       Else         Set c = Wb.Sheets("Sheet2").Range(Target.Value). _           Find(Target.Offset(0, 1).Value, lookat:=xlWhole)         If c Is Nothing Then           'Target.Offset(0, 1).Valueが見つからなければ           Target.Offset(0, 1).Value = ""         Else           '↑見つからなかった時の処理だけで見つかった時は?           MsgBox c.Address(External:=True) & " にミッケ"         End If       End If     End If     If Target.Column = 2 Then       If Target.Value = "" Then         Target.Offset(0, -1).Value = ""       End If     End If     Application.EnableEvents = True   End If End Sub

ampm2007
質問者

お礼

ご教示頂いたコードで確かにエラーにはなりませんでしたが、 肝心のSub Macro2()が利用できずに、 当方の求めている動作にはなりませんでした。

  • HohoPapa
  • ベストアンサー率65% (454/691)
回答No.3

>別ブックからデータを参照する方法 やりたいことの要は、 添付画像を例にすれば、 =IF(A2="",A2,INDIRECT(A2)) なかでも、 INDIRECT(A2) この記述で、"果物"という名前を持つ範囲名のセル群を 自ブックではなく、同時に開いている別なブックから探してくれるか? ということと思います。 詳しく確認したことはありませんが、 複数のブックが開いている可能性もありますので、 エクセルは、そこまでは賢くないだろうと思います。 少なくとも私が行ってみる限り探してくれません。 また、 =IF(A2="",A2,INDIRECT(A2)) を =IF(A2="",A2,INDIRECT([候補群.xlsx]Sheet1!$B$2:$B$6)) と書き換えることも許してくれません つまり、セルの入力規則に使う候補群を 別なブックのセル範囲から得たいのであれば、 http://www.eurus.dti.ne.jp/yoneyama/Excel/vba/vba_validation.html この延長上では実現するのは、非常に厳しと思います。 やるとすれば、例えば、 入力規則を設定するブックが開くときに マクロで候補群の埋まったブックも開き 必要なセル範囲の候補群たちを自シートに複写するとか 配列変数に格納しながら、A2セルの候補群を埋め その後、Worksheet_Changeのイベントを使い、 B2セルの入力規則の候補群フィールドに 動的に、候補群を埋め込む必要があるものと思います。 (少なくとも私はこの方法で実現しています。)

ampm2007
質問者

お礼

Set c = Wb.Sheets("Sheet2").Range(Target.Value).Find(Target.Offset(0, 1).Value, lookat:=xlWhole) を With Wb.Sheets("リスト") lCol = .Cells.Find(Target).Column Set c = .Columns(lCol).Find(Target.Offset(0, 1).Value, lookat:=xlWhole) End With に改変することで思い通りの動作が確認できましたが、不安です。

ampm2007
質問者

補足

まさに、 入力規則を設定するブックが開くときに マクロで候補群の埋まったブックも開き 必要なセル範囲の候補群たちを 元ブック側に定義する という方法を取っています。

  • watabe007
  • ベストアンサー率62% (476/760)
回答No.2

>同ブックの別シートではRange(Target.Value)で探せるのに・・・ Workbooks("MyBook.xls")に正しく範囲名が設定されているのか確認した方が よいです。 >ActiveWorkbook.Names("項目リスト").Delete >ActiveWorkbook.Names.Add Name:="項目リスト", _ この場合、MyBook.xlsは、アクティブにはなっていないでしょう Wb.Names("項目リスト").Delete Wb.Names.Add Name:="項目リスト", Sub name_1()   Dim lCol As Long, lRow As Long   Dim i As Long, nName As String   Dim Wb As Workbook   Set Wb = Workbooks("MyBook.xls")   On Error Resume Next   With Wb.Sheets("Sheet2")     lCol = .Range("A1").End(xlToRight).Column     Wb.Names("項目リスト").Delete     Wb.Names.Add Name:="項目リスト", _       RefersTo:=.Range(.Cells(1, 1), .Cells(1, lCol))     '----名前の定義     For i = 1 To lCol       lRow = .Cells(1, i).End(xlDown).Row       nName = .Cells(1, i).Value       Wb.Names(nName).Delete       .Range(.Cells(1, i), .Cells(lRow, i)).CreateNames Top:=True     Next i   End With End Sub

ampm2007
質問者

補足

ご指摘の通り、名前の定義は元ブックに作られていました。 が、MyBook.xlsに定義を作ると入力規則で名前の指定が出来なくなってしまいます(外部指定が出来ない)。 なので、以下のように書き換えました。 Sub name_1() Dim lCol As Long, lRow As Long Dim i As Long, nName As String Dim Wb As Workbook Set Wb = Workbooks("Book2.xlsx") On Error Resume Next With Wb.Sheets("リスト") lCol = .Range("A1").End(xlToRight).Column ActiveWorkbook.Names("項目リスト").Delete ActiveWorkbook.Names.Add Name:="項目リスト", _ RefersTo:=.Range(.Cells(1, 1), .Cells(1, lCol)) For i = 1 To lCol lRow = .Cells(1, i).End(xlDown).Row nName = .Cells(1, i).Value ActiveWorkbook.Names(nName).Delete ActiveWorkbook.Names.Add Name:=nName, _ RefersTo:=.Range(.Cells(2, i), .Cells(lRow, i)) Next i End With End Sub この場合の Set c = Wb.Sheets("Sheet2").Range(Target.Value).Find(Target.Offset(0, 1).Value, lookat:=xlWhole) は、どのように書き換えるのでしょうか?

  • watabe007
  • ベストアンサー率62% (476/760)
回答No.1

なぜエラーが出たのか探ってみては Set c = Wb.Sheets("Sheet2").Range(Target.Value).Find(Target.Offset(0, 1).Value, lookat:=xlWhole) ←ここでエラー    ↓ On Error Resume Next Set c = Wb.Sheets("Sheet2").Range(Target.Value).Find(Target.Offset(0, 1).Value, lookat:=xlWhole) If Err Then MsgBox Wb.Name & "のSheet2の範囲名:" & Target.Value & " から" & vbCrLf & _ Target.Offset(0, 1).Value & " を探していますが間違いないですか?" Application.EnableEvents = True Exit Sub End If On Error GoTo 0

ampm2007
質問者

お礼

試してみました。 Wb.Name=sheet2 Target.Value=項目2 Target.Offset(0, 1).Value=2-1 と、間違いなく、こちらの意図している文字列を探しに行っているように見えたのですが、どうやらRange(Target.Value)がダメなようです。 Targetが項目1ならA列から、 Targetが項目2ならB列から、 一致する文字列を探したいです。 同ブックの別シートではRange(Target.Value)で探せるのに、 別ブックにすると、なぜダメなのでしょうか?

ampm2007
質問者

補足

ご教示有難うございます。 確認できる環境に居ないので、週明けに試してみます。 ちなみに、エラー内容は『アプリケーション定義またはオブジェクト定義のエラー』です。

関連するQ&A

  • Excel VBA 入力規則

    入力規則を利用して、3つのセルを連携させることを考えていますが、 不適合な値を張り付けらられた場合に拒否をする方法があるのでしょうか。 Private Sub Worksheet_Change(ByVal Target As Range) Dim ad As String Dim ma As Range Dim ma2 As Range Dim r As Range Dim r2 As Range Dim r3 As Range Dim r1 As Range Dim m As Long Dim m2 As Long Application.EnableEvents = False If Target = "" Then Range("F7").Validation.Delete Range("F7") = "" If Target.Address(0, 0) = "B7" Then Range("D7").Validation.Delete Range("D7") = "" End If GoTo EXIT_SUB End If With Worksheets("Sheet1") ad = "A4" Set r = .Range(ad) Set ma = r.MergeArea Set r1 = r.Offset(0, 1) m = Application.Match(Range("B7"), .Range(r1, .Cells(r.Row + ma.Count - 1, r1.Column)), 0) Set r2 = .Cells(r.Row + m - 1, r1.Column) Set ma2 = r2.MergeArea If Target.Address(0, 0) = "B7" Then If ma.MergeCells Then setValiS Target.Offset(0, 2), r2 Range("F7").Validation.Delete Target.Offset(0, 2) = "" Target.Offset(0, 4) = "" Else MsgBox "A列が連結されていません。" End If ElseIf Target.Address(0, 0) = "D7" Then Set r3 = r2.Offset(0, 1) m2 = Application.Match(Target, .Range(r3, .Cells(r2.Row + ma2.Count - 1, r3.Column)), 0) setValiS Target.Offset(0, 2), .Cells(r2.Row + m2 - 1, r3.Column) Target.Offset(0, 2) = "" End If End With EXIT_SUB: Application.EnableEvents = True End Sub Sub setVali2() Dim tc As Range Dim c As Range Set tc = Worksheets("登録").Range("D3") Set c = Worksheets("Sheet1").Range("C3") setValiS tc, c End Sub Sub setValiS(tc As Range, c As Range) Dim ss As String Debug.Print tc.Address, c.Address ss = getChildren(c) If ss > "" Then With tc.Validation .Delete .Add Type:=xlValidateList, Formula1:=getChildren(c) End With End If Worksheets("登録").Activate End Sub Function getChildren(c As Range) Dim c1 As Range Dim ss As String Dim s1 As String Worksheets("Sheet1").Activate ss = "" For Each c1 In c.MergeArea s1 = c1.Offset(0, 1) If s1 <> "" Then ss = ss & "," & s1 Next c1 If ss <> "" Then ss = Mid(ss, 2) Else MsgBox "データがありません!" End If getChildren = ss End Function Sub Outline() Dim CheckRow As Long Dim Moji As String Dim TopRow As Long Dim EndRow As Long With ActiveSheet .Range("A2").ClearOutline .Outline.SummaryRow = xlAbove CheckRow0 = .Range("A" & .Rows.Count).End(xlUp).Row CheckRow = CheckRow0 Do If Moji = "" Then Moji = .Cells(CheckRow, 1).Value EndRow = CheckRow ElseIf yy_mm(CDate(.Cells(CheckRow, 1).Value)) = yy_mm(CDate(Moji)) Then TopRow = CheckRow If TopRow = 1 Then .Rows(TopRow + 1 & ":" & EndRow).Rows.Group Exit Do End If Else .Rows(TopRow + 1 & ":" & EndRow).Rows.Group CheckRow = CheckRow + 1 Moji = "" End If CheckRow = CheckRow - 1 Loop Until CheckRow = 1 .Rows(CheckRow + 1 & ":" & EndRow).Rows.Group .Outline.ShowLevels RowLevels:=1 ExecuteExcel4Macro "SHOW.DETAIL(1," & CheckRow0 & ",TRUE)" End With End Sub Function yy_mm(d As Date) yy_mm = Format(d, "yy/mm") End Function

  • 配列のフリーズを解消してください。

    Sub データ原本() Dim wsAll As Worksheet Set wsAll = Worksheets("All(5)") Dim lRow As Long, lCol As Long Dim i As Long, j As Long, cnt As Long With Worksheets("データ原本") '日付S行を日付に変更(「.」を「/」に置換) lRow = .Cells(Rows.Count, 1).End(xlUp).Row Dim MyArray As Variant MyArray = Range(.Cells(10, 1), .Cells(lRow, 1)) For i = 1 To lRow - 9 MyArray(i, 1) = Replace(MyArray(i, 1), ".", "/") Next Range(.Cells(10, 1), .Cells(lRow, 1)) = MyArray Erase MyArray '配列の初期化 '「天気」両サイドの &「内・外」両サイドの空白スペースを削除 lRow = .Cells(Rows.Count, 1).End(xlUp).Row MyArray = Range(.Cells(10, TNK), .Cells(lRow, TNK)) For i = 1 To lRow - 9 MyArray(i, 1) = Trim(MyArray(i, 1)) Next Range(.Cells(10, TNK), .Cells(lRow, TNK)) = MyArray Erase MyArray '配列の初期化 '数値0のデータ行の行削除 lRow = .Cells(Rows.Count, 1).End(xlUp).Row lCol = .Cells(9, Columns.Count).End(xlToLeft).Column Dim arr_A As Variant, arr_B As Variant arr_A = Range(.Cells(9, 1), .Cells(lRow, lCol)).Value ReDim arr_B(1 To lRow - 8, 1 To lCol) cnt = 0 For i = 1 To lRow - 8 If arr_A(i, 18) <> 0 Then cnt = cnt + 1 For j = 1 To lCol arr_B(cnt, j) = arr_A(i, j) Next j End If Next i .Range("A9").Resize(lRow, lCol).Value = arr_B End With End Sub  上記のコードを2回実行すると2回目には、 MyArray(i, 1) = Replace(MyArray(i, 1), ".", "/")のところで「型が一致しません。」とフリーズします。かと言って 「 '数値0のデータ行の行削除」コードを一括削除して、実行ボタンを何度押してもフリーズすることはありません。どこに不具合が生じているのかわからないのですが、どなたか名回答を宜しくお願いします。

  • 2つのVBAを組み合わせる方法

    お世話になります、2つのVBAを組み合わせる方法で迷っています。 1つ目が Private Sub Worksheet_Change(ByVal Target As Range) Dim i As Long, k As Long, myNum As Long If Intersect(Target, Range("C1,B9:B39")) Is Nothing Or Target.Count > 1 Then Exit Sub Application.EnableEvents = False With Target If .Column = 3 Then myNum = WorksheetFunction.Max(Range("B9:B39")) If IsDate(.Value) Then For i = 9 To 39 If Cells(i, "A").Value = "" Then Cells(i, "B").Value = "" Else Cells(i, "B") = myNum + i - 8 End If Next i End If Else i = .Row If .Value = "" Then Range(Cells(i + 1, "B"), Cells(39, "B")).ClearContents Else For k = i + 1 To 39 If Cells(k, "A").Value = "" Then Cells(k, "B").Value = "" Else Cells(k, "B") = Cells(k - 1, "B") + 1 End If Next k End If End If End With Application.EnableEvents = True End Sub です。 2つめが Private Sub Worksheet_Change(ByVal Target As Range)  Application.EnableEvents = True If Intersect(Target, Range("R8:R38")) Is Nothing Then Exit Sub Application.EnableEvents = False Range(Cells(Target.Row, 18), Cells(39, 18)).Value = Target.Value Application.EnableEvents = True End Sub です。2つのPrivate Sub Worksheet_Change(ByVal Target As Range)イベントのVBAですが、どのようにして組み合わせれば良いのでしょうか?

  • 特定の文字以外を入力すると別シートに表記する方法

    Option Explicit Private Sub Worksheet_Change(ByVal Target As Range) Dim StrRow As Long Dim TgtCol As Long Dim MaxRow As Long Dim ChgRow As Long Dim PutSh1 As Worksheet Dim PutSh2 As Worksheet Dim PutSh3 As Worksheet Dim PutCol As Long Dim PutRow As Long Dim ChgRng1 As Range Dim ChgRng2 As Range Dim ChgRng3 As Range StrRow = 5 MaxRow = 35 If Target.Count > 1 Then Exit Sub If Target.Value = "" Then Exit Sub Set PutSh1 = ThisWorkbook.Sheets("Sheet2") Set PutSh2 = ThisWorkbook.Sheets("Sheet3") Set PutSh3 = ThisWorkbook.Sheets("Sheet4") With ThisWorkbook.Sheets("Sheet1") Set ChgRng1 = Range(.Cells(StrRow, 3), .Cells(MaxRow, 3)) 'C列 Set ChgRng2 = Range(.Cells(StrRow, 5), .Cells(MaxRow, 5)) 'E列 Set ChgRng3 = Range(.Cells(StrRow, 7), .Cells(MaxRow, 7)) 'G列 End With ChgRow = Target.Row If Not Intersect(Target, ChgRng1) Is Nothing Then Target.Offset(0, -1).Value = Target.Offset(0, -1).Value + 1 DataPut PutSh1, ChgRow, Target.Value End If If Not Intersect(Target, ChgRng2) Is Nothing Then Target.Offset(0, -1).Value = Target.Offset(0, -1).Value + 1 DataPut PutSh2, ChgRow, Target.Value End If If Not Intersect(Target, ChgRng3) Is Nothing Then Target.Offset(0, -1).Value = Target.Offset(0, -1).Value + 1 DataPut PutSh3, ChgRow, Target.Value End If End Sub 以前質問させて頂いた内容で追加の質問です。 Sheet1の指定したセルに「ー(ハイフン)」の文字がある時は、Sheet2〜4に転送(表記)しない方法を追加する場合はどの様にすれば宜しいでしょうか?

  • エクセル ダブルクリックで処理日の入力

    お世話になります。 先般、お教え頂きました別のダブルクリックイベントプロシージャと 下記の当日の日付を入力するという処理を同じシート上で行いたいのですが、VBエディターにどのように記述したら良いかわかりません。 当方、かなりの初心者です。 よろしくご教授くださいませ。 【新しく加えたい処理】 Option Explicit Private Sub Worksheet_BeforeDoubleClick(ByVal Target As Range, Cancel As Boolean) If Intersect(Target, Range("b4:C999")) Is Nothing Then Exit Sub If ActiveCell = "" Then ActiveCell = Date Cancel = True End If End Sub 【もともと使っている処理】 Private Sub Worksheet_BeforeDoubleClick(ByVal Target As Range, Cancel As Boolean) If Not Intersect(Target, Range("h1:h999")) Is Nothing Then With Target If .Value = "" Then .Value = "有" ElseIf .Value = "有" Then .Value = "無" ElseIf .Value = "無" Then .Value = "" End If End With ElseIf Not Intersect(Target, Range("i1:i999")) Is Nothing Then With Target If .Value = "" Then .Value = "要" ElseIf .Value = "要" Then .Value = "不要" ElseIf .Value = "不要" Then .Value = "" End If End With End If End Sub よろしくお願いします。

  • VBAについて

    以下のプログラムは、1年間の価格合計を求めるプログラムです。 これを実行するとうまくいくこともありますが、エラーが起きることもあります。 どうやら下記コードが原因のようなのですが、間違いがわかりません。 Target.Offset(0, 1).Value = run * (13 - month) どこが間違っているのでしょうか。 また最終的に、A行かB行のどちらかが更新されたときにこのプログラムを 実行させたいのですが、方法がわかりません。 無知な質問ではありますが、どなたか教えてください。 --------------------------------------------------------- Private Sub Worksheet_Change(ByVal Target As Range) Dim month As Integer Dim run As Integer If Intersect(Target, Range("A25:A35")) Is Nothing Then Exit Sub Else If Target.Offset(0, -2).Value <> "" Then month = Target.Offset(0, -2).Value month = month - 3 If month = -2 Then month = 10 ElseIf month = -1 Then month = 11 ElseIf month = 0 Then month = 12 End If run = Target.Offset(0, 0).Value Target.Offset(0, 1).Value = run * (13 - month) End If End If End Sub

  • こんばんは、watabe007さん。

    961awaawaです。 >シートモジュールに貼り付けてお試しください。 Private Sub Worksheet_Change(ByVal Target As Range) With Target If Intersect(.Cells, Range("L:M")) Is Nothing Then Exit Sub If .Row < 3 Or .Value = "" Then Exit Sub If Not IsNumeric(.Value) Then Exit Sub .Offset(, 3).Value = Cells(.Row, .Value).Value End With End Sub というソースを作って頂いたのですが、既に各sheetにprivate sub からなるソースが入ってましてコンパイルエラー(名前が適切ではありません Worksheet_Change)となります。他に方法等頂けましたらありがたいです。

  • 入力用のセルと管理用のセルを分けるには??

    Private Sub Worksheet_Change(ByVal Target As Range) Dim myC As String Dim x As Range   If Intersect(Target, Range("A1,C2,D4")) Is Nothing Then Exit Sub   Select Case Target.Address(0, 0)     Case "A1": myC = "E"     Case "C2": myC = "F"     Case "D4": myC = "G"   End Select   If Cells(Rows.Count, myC).End(xlUp).Value = "" Then     Set x = Cells(Rows.Count, myC).End(xlUp)   Else     Set x = Cells(Rows.Count, myC).End(xlUp).Offset(1)   End If   x.Value = Target.Value End Sub 入力用セルと、管理用のセルを分けたい・・・・・ という質問をしてこのマクロを教えていただいたんですが、 実際には入力用にしたいセルが、40箇所以上ありまして 一つ一つ反映させるのではなく、すべての箇所に入力して確認後に まとめて反映させたいのですが不可能でしょうか?? 何か方法があるようでしたらヨロシクお願いします!! エクセル2003です。

  • Excel マクロのFor~Nextで再起動エラー

    勤務表を作っています。 下記の’OKまでは希望どうりうまく出来ていたのですが、勤務表の下セルに各列の人員(行)10名分位A,B,Cの計を表示させたい。実行するとエラー「Microsoft office Excel 再起動」を求められます。  for~が判断指令が<重い>のでしょうか。なんとか回避さする方法を教えてください。 Win XP Sp2 Office Excel 2007です。今回これを作るにあたり初VBA使用者です。 ' C入力後の翌日は休をセット。CC連続は休休セット。 Private Sub Worksheet_Change(ByVal Target As Range) Dim cnt As Variant Dim a1 As Byte Dim b1 As Byte Dim c1 As Byte Dim nin As Variant Dim retsu As Variant If Target.Count > 1 Then Exit Sub '複数セルの入力は無視 'A If Target.Value = "A" Or Target.Value = "A" Then Target.Value = "A" Range("AV16").Value = Target.Column End If 'B If Target.Value = "B" Or Target.Value = "B" Then Target.Value = "B" Range("AV16").Value = Target.Column End If 'C If Target.Value = "C" Or Target.Value = "C" Then Range("AV16").Value = Target.Column Target.Value = "C" Else End If ' If Target.Value = "C" Then If Target.Offset(0, -1).Value = "C" Then 'Cが連続したら Target.Offset(0, 1).Resize(1, 2).Value = ("休") '連休に Else End If Target.Offset(0, 1).Value = ("休")   'そうでなければ休 End If 'A,B,C の数をカウントする。 nin = Range("AV15")  '別のプログラムから入力した人員数 retsu = Range("AV16")  ' A,B,Cのいずれかを入力したセル列。Target.Column ’OK For cnt = 7 To (6 + nin) If cells(cnt, retsu) = "A" Then a1 = a1 + 1 End If If cells(cnt, retsu) = "B" Then b1 = b1 + 1 End If If cells(cnt, retsu) = "C" Then c1 = c1 + 1 End If Next cnt cells(nin + 7, retsu) = a1 'A番 cells(nin + 8, retsu) = b1 'B番 cells(nin + 9, retsu) = c1 'C番 End Sub

  • 空白セルと0値を識別させたい。(VBA)

    すみません、誰か教えていただけますか。 シートの53、54、55行目にそれぞれ値入っています。 それを3行目にビジュアル的に表現させています。 55行目はセルの色で、53行目は数値があり同じ値が 続く部分の合計を出しています。 しかし、下記の記述ですと数値が0(変数D=0)の時に うまくいきません。空白セルと認識されてしまうと思います。 何か、良い方法があれば教えて頂けませんでしょうか。 宜しくお願いします。 Sub 表示() Dim a As Long Dim c As Long Dim D As Long Dim e As String Dim f As String c = 3 For a = 3 To 64 With Worksheets("Sheet1") If .Cells(53, a) <> .Cells(53, a + 1) Then .Range(.Cells(53, c), .Cells(53, a)).Select D = WorksheetFunction.Sum(Selection) e = D f = Selection(1).Offset(1, 0).Value G = Selection(1).Offset(2, 0).Value If D <> 0 Then Selection(1).Offset(-50, 0).Value = f + "//" + e .Range(.Cells(53, c), .Cells(53, a)).Offset(-50, 0).Select Selection.Interior.ColorIndex = G End If If Selection(1).Value = "" Then .Range(.Cells(53, c), .Cells(53, a)).Offset(-50, 0).Select Selection.ClearContents Selection.Interior.ColorIndex = xlNone End If c = a + 1 End If End With Next End Sub

専門家に質問してみよう