Vlookup worksheet function in VBA (runtime error 9) - vba

I'm new to VBA and I have the following code for a function :
Function checktype(ByVal modele As String)
Dim srchRange As Range
Dim book1 As Workbook
'Set some Workbook variables:
Set book1 = Workbooks("C:\Users\MZ\Desktop\EPI.xlsx")
Set srchRange = book1.Sheets(1).Range("A1:D800")
'This assumes that the Book2 is Open and you are on the desired active worksheet:
checktype = Application.WorksheetFunction.VLookup(modele, srchRange, 4, False)
End Function
The aim of this code is to get a certain number from another workbook using Vlookup function and return the value to the function checktype.
The problem is that I get a runtime error 9. When I click Debug the following line gets highlighted :
Set book1 = Workbooks("C:\Users\MZ\Desktop\EPI.xlsx")

Either make sure that the workbook is opened in the same instance of excel and refer it like this:
Set book1 = Workbooks("C:\Users\MZ\Desktop\EPI.xlsx")
Set book1 = Workbooks("EPI.xlsx") 'specifying only the name is OK as well
or
Set book1 = Workbooks.Open("C:\Users\MZ\Desktop\EPI.xlsx")
An example of 2 Excel files in the same instance:

Related

Excel vba variable not defined when using range variable

I have function testFunc that takes Range as an argument, loops thorugh its cells and edits them. I have sub testSub that tests two cases: first is when I pass the current workbook's range to testFunc through: 1. variable Range 2. just as an argument testFunct(...Range("A1:A16")).
The second case is when I open another workbook and do the same - pass one of its worksheets range to the testFunc directly or via variable.
Function testFunc(aCol As Range)
Dim i As Integer
i = 0
For Each cell In aCol
MsgBox (cell.Value)
cell.Value = i
i = i + 1
Next
testFunc = i
End Function
Sub testSub()
Dim origWorkbook As Workbook
Set origWorkbook = ActiveWorkbook
Dim aRange As Range
Set aRange = ThisWorkbook.Sheets("sheet 1").Range("A1:A16")
Dim dataWorkbook As Workbook
Set dataWorkbook = Application.Workbooks.Open("Y:\vba\test_reserves\test_data\0503317-3_FO_001-2582480.XLS")
Dim incomesNamesRange As Range
Set incomesNamesRange = dataWorkbook.Worksheets("sheet 1").Range("A1:A20")
' origWorkbook.Worksheets("sheet 1").Cells(1, 5) = testFunc(dataWorkbook.Sheets("1").Range("A1:A20"))
origWorkbook.Worksheets("Ëèñò2").Cells(1, 50) = testFunc(incomesNamesRange)
' testFunc aRange
'origWorkbook.Worksheets("sheet 1").Cells(1, 5) = testFunc(aRange) '<---good
' origWorkbook.Worksheets("sheet 1").Cells(1, 5) = testFunc(ThisWorkbook.Sheets("sheet 1").Range("A1:A16"))
End Sub
The problem is, as I indicated with comments, when I open a foreign workbook and pass its range through a variable it gives an error variable not definedFor Each cell In aCol`, while all other cases (including passing range variable of the current workbook) work fine.
I need testFunc to stay a Function, because it's a simplfied example of some code from bigger program which needs to take a returned value from a function. And I need to store that Range in a variable too, to minimize time of the execution.
EDIT: As pointed out in the comments, I replaced Cells(1,5) with origWorkbook.Worksheet("shee t1").Cells(1,5) and fixed variable name, but the original mistake changed to variable not defined. I edited the title and body of the question.
The default name for the worksheet shouldn't have a space in it.
Set incomesNamesRange = dataWorkbook.Worksheets("sheet 1").Range("A1:A20")
Change this to:
Set incomesNamesRange = dataWorkbook.Worksheets("Sheet1").Range("A1:A20")
And see if that fixes it.

Copy a specific range from a source worksheet to a target worksheet with different path

Dim path_feb As String
Dim path_mar As String
Dim wkbk_feb As Workbook
Dim wkbk_mar As Workbook
path_feb = "D:\Tranzit\2016\feb\data_feb.xlsx"
Set wkbk_feb = Workbooks.Open(path_feb)
path_mar = "D:\Tranzit\2016\mar\data_mar.xlsx"
Set wkbk_mar = Workbooks.Open(path_mar)
Worksheets("monthly").Range("A2:A1000").Value = Windows("wkbk_feb").Worksheet("impuls").Range("A2:A1000").Value
Worksheets("monthly").Range("B2:B1000").Value = Windows("wkbk_mar").Worksheet("impuls").Range("A2:A1000").Value
End Sub
I need a little help to work this code.
The issue begin here:
Worksheets("monthly").Range("A2:A1000").Value = Windows("wkbk_feb").Worksheet("impuls").Range("A2:A1000").Value
So, I have 3 files with different path:
D:\Tranzit\2016\feb\data_feb.xlsx
D:\Tranzit\2016\\mar\data_mar.xlsx
D:\Tranzit\2016\data_final.xlsm
I want to copy from file 1 the range A2:A1000 from "Sheet" Impuls to file 3 in range A2:A1000 from "Sheet" monthly.
and
copy from file 2 the range A2:A1000 from "Sheet" Impuls to file 3 in range B2:B1000 from "Sheet" monthly.
You declared wkbk_feb and wkbk_mar as workbook objects so you need to reference them directly:
wkbk_feb.Worksheets("impuls")....
instead of activating or selecting anything you should always specify the workbook or worksheet. So it should look something like
wkbk_total.Worksheets("monthly")... = wkbk_feb.Worksheets("impuls")....

Using Select Case in Excel VBA To Copy Worksheet from Closed Workbook

Hello I am trying to write an excel VBA script that will copy a specific worksheet from a closed workbook to the active workbook. The sheet to copy is determined by a checkbox and the value of a variable that is set to be the text in a specific cell. My code:
Sub copysheet()
Dim WB, ClosedWB as Workbook
Set CheckBox = ActiveSheet.Shapes("CheckBox").DrawingObject
Model = ActiveSheet.Range("K3").Text
Const FilePath = "C:\..."
Set WB = Application.Workbooks.Open(FilePath, UpdateLinks:=False, ReadOnly:=False, AddToMRU:=False)
If CheckBox.Value = xlOn Then
With ClosedWB
Select Case Model.Text
Case Model = Sheet1
Sheets("Sheet 1 Name").Copy After:=Workbooks(WB).Sheets(Workbooks(WB).Sheets.Count)
Case Model = Sheet2
Sheets("Sheet 2 Name").Copy After:=Workbooks(WB).Sheets(Workbooks(WB).Sheets.Count)
End Select
End With
End If
If CheckBox.Value = xlOff Then
With ClosedWB
Select Case Model.Text
Case Model = Sheet3
Sheets("Sheet 3 Name").Copy After:=Workbooks(WB).Sheets(Workbooks(WB).Sheets.Count)
Case Model = Sheet4
Sheets("Sheet 4 Name").Copy After:=Workbooks(WB).Sheets(Workbooks(WB).Sheets.Count)
End Select
End With
End If
I am getting a Run-Time error '424': Object Required and it highlights the Select Case Model.Text line. I have also tried Select Case Model.Value, but that didn't work. If I create a MsgBox to display the variable model, then it displays whatever is written in the appropriate cell, so the variable value is being stored. Please help I am new at this.
Edit: Modifying Select Case Model.Text to just Select Case Model no longer results in a run-time error, but the sheets will not copy. When I run the script, it opens up the new workbook (ClosedWB), but does nothing after that. It doesn't even select the sheet that I specified it to. How can I get this to work?
Model is a string since you assigned it ActiveSheet.Range("K3").Text. I strongly suggest you insert Option Explicit at the top of your module, and always compile before running. (Tools, Options, Require variable Declaration will do it automatically in every new module).
Select Case Model
You are also trying to compare a string to a sheet. Either you need to put the sheet# part in quotes if that is the text that is being entered or use sheet1.name.

User Defined Function to VLookup into Closed Workbook

I'm attempting to create a User Defined Function to vlookup into a closed workbook on my machine. The below function works while testing it in VBA, but I get the #VALUE error in Excel when attempting to use the function. Any ideas on this? I believe I may be able to use the VBA Evaluate function to help, but so far have had no luck.
Function CUSIP_Deal_Map(CUSIP As String, DataField As String) As Variant
Dim colIndex As Integer ' for vlookup
Dim invalidDataField As Boolean
invalidDataField = False
' Switch statement, to transform from a "DataField" into a column number to be used in VLookUp
Select Case DataField
Case "Deal"
colIndex = 2
Case "Class"
colIndex = 5
Case "DealNum"
colIndex = 6
Case "Vintage"
colIndex = 11
Case "Pool"
colIndex = 12
Case "Index"
colIndex = 13
Case Else
invalidDataField = True
End Select
'Dim wbk As Workbook
Set wbk = Workbooks.Open("C:\CUSIP_Map.xlsx") 'hard code location
Dim VLU_data As Variant
VLU_data = wbk.Application.WorksheetFunction.VLookup(CUSIP, Worksheets("CUSIP_Map").Range("A:M"), colIndex, False) 'vlookup data from "database"
Call wbk.Close(False) 'close connection
' Return data
If invalidDataField Then
CUSIP_Deal_Map = "Invalid DataField"
Else
CUSIP_Deal_Map = VLU_data
End If
End Function
The intended use in Excel would be to utilize a formula like =CUSIP_Deal_Map("123ABC","Deal")
I can test this in VBA, using this code, which returns the value I'm expecting:
Sub test()
MsgBox CUSIP_Deal_Map("123ABC", "Deal")
End Sub
Still, this doesn't work within Excel itself. I found a "pull" UDF online which seems to do something similar, but have been unsuccessful modifying it for my purposes.
That is because a UDF() call from within a Sub can open a file, but the same UDF() called from a worksheet cell cannot.
EDIT#1:
insure the UDF is in a standard module.
at the very top of the module include Public wbk as Workbook
create a workbook Open event macro in your workbook code area to open the secondary workbook and initialize wbk
OK, with the limitation already brokered by Gary's Student, you may want to rethink the idea of a UDF altogether. With those values from the Select Case statement in the first row of the closed CUSIP_Map worksheet, either of these standard worksheet formulas will do.
=VLOOKUP(A1, 'C:\[CUSIP_Map.xlsx]CUSIP_Map'!$A:$M, MATCH("Vintage", 'C:\[CUSIP_Map.xlsx]CUSIP_Map'!$1:$1, 0), FALSE)
=VLOOKUP(A1, 'C:\[CUSIP_Map.xlsx]CUSIP_Map'!$A:$M, LOOKUP("Class", {"Class","Deal","DealNum","Index","Pool","Vintage"}, {5,2,6,13,12,11}), FALSE)
A1 would be value to look up in the CUSIP_Map's column A. Instead of a VBA select case, the column to return is determined by either a MATCH function of the first row column headers or a hard-coded LOOKUP function of text and column numbers. Note that the LOOKUP has its values in ascending order and that it may not have as much error control as the MATCH as it will attempt partial matches. An IFERROR function as a wrapper can return "Invalid DataField" on MATCH errors.

Excel VBA Can't access sheet on external workbook

I have created a custom function in Excel using VBA. I'm trying to get data from a different workbook using the Workbooks.Open(path) command. Here's my code:
Option Explicit
Function TestFunction() As String
mySub
TestFunction = "Success."
End Function
Sub mySub()
Dim path As String
Dim wk As Workbook
path = "C:\Users\jg\Desktop\machine_data.xlsm"
Set wk = Workbooks.Open(path)
Dim ws As Worksheet
Set ws = wk.Sheets(1)
Debug.Print ws.Range("A2")
End Sub
Sub Test()
Debug.Print (TestFunction())
End Sub
Now my problem is the following:
When I run the Sub Test() within the VBA environment from Excel everything works as planned. machine_data.xlsm gets opened and the field A2 shows up in debug.
Once I go to the workbook where I defined this module in and type =TestFunction() into a cell, I get a #VALUE!. The file also doesn't get opened.
If I comment these two lines:
Set ws = wk.Sheets(1)
Debug.Print ws.Range("A2")
the cell will show Success!, but the file still doesn't open.
What am I doing wrong? Both workbooks are .xlsm files. I am using Microsoft Office Excel 2007.
Just throw everything from mySub into the test function and if everything is successful have test function return the value of the cell. So testFunc = ws.Range("A2").
As DaveU already stated UDFs can only return values. I found a different workaround simply calling the function from within the VBA environment which lets me modify cell contents wherever I'd like.