I am writing a VBA code to read some text files, I would like the file names to be read directly from cells in excel.
I used the following code
Sub ImportFile()
Const textFilePath As String = "C:\Desktop\"
Const textFileName As String = "File1.txt"
Const newTextFileName As String = "NewFile1.txt"
I want to have something like
Sub ImportFile()
Const textFilePath As String = Range("A2").value
Const textFileName As String = Range("A3").value
Const newTextFileName As String = Range("A4").value
I tried different combinations but it does not seem to like the idea of assigning a constant to a cell value, any work around?
Thanks
P.S I don't know how to write the code in a correct way in this website, I tried to add 4 spaces before the code lines but did not seem to work, any idea why?
I don't think you can assign a constant from a range because the range value could change during your code execution. I tried your declarations in this bit of code:
Option Explicit
Sub ImportFile()
Const textFilePath As String = Range("A2").Value
Const textFileName As String = Range("A3").Value
Const newTextFileName As String = Range("A4").Value
End Sub
and on Debug..Compile in the IDE I got this error
If you change your code to
Option Explicit
Sub ImportFile()
Dim textFilePath As String
Dim textFileName As String
Dim newTextFileName As String
textFilePath = Range("A2").Value
textFileName = Range("A3").Value
newTextFileName = Range("A4").Value
End Sub
You'll find it compiles OK.
Unless you're talking "Universal (physical) constants" like PI,c or G for example, constants rarely are constant. I've found that having a named range, possibly on a hidden sheet, and populating a variable from that named range makes for easier maintenance by users with little no VBA experience. Sure, you need to keep track of those "constants" to maintain them but at least you don't need VBA experience to do so.
You can't do that in vba since your constant variables might change. However, I think that you want to declare and initialize your path variables once so that later if you decide to change them you can do that in one place in the same row where the variable was initialized. So If I were you I would use something like
Option Explicit
sub macro()
Dim FILEPATH As String: FILEPATH = Range("A1").Value
MsgBox FILEPATH
end sub
Related
I have a function in excel that gives hour of last modification using path , only one part of the path changes exp:
\c:\xcl\report\sudtrack\20200324\dossier22
the part is 20200324
i want to do something like that : function('20200324') the code will place it in the path
path="\\c:\xcl\report\sudtrack\" & 20200324 &"\dossier22"
my current code
Function End_hour(path As String)
End_hour = Format(FileDateTime(path), "hh:mm:ss")
End Function
i want to do something like that : function('20200324') the code will place it in the path
No need to use use a function. You can directly do a Replace. Just set up a base string as shown below and do the replace.
Option Explicit
Sub Sample()
Dim myPath As String
myPath = "\\c:\xcl\report\sudtrack\HOUROFLASTMOD\dossier22"
MsgBox Replace(myPath, "HOUROFLASTMOD", "20200324")
End Sub
Note: I have used HOUROFLASTMOD. You can change it to whatever string you want.
If you still want to use a function then try this
Option Explicit
Sub Sample()
MsgBox ReturnNewPath("20200324")
End Sub
Function ReturnNewPath(TimeString As String)
Dim myPath As String
myPath = "\\c:\xcl\report\sudtrack\HOUROFLASTMOD\dossier22"
ReturnNewPath = Replace(myPath, "HOUROFLASTMOD", TimeString)
End Function
So my macro uses many string constants to store the filenames of workbooks I want to edit. Each variable uses the naming convention template and then a 3 digit number (e.g. template001). Is there a way I can use an integer variable to refer to which constant I want to use? I'm imagining something like this:
Public Const filepath = "C:\Templates\"
Public Const template001 = "001.xls"
Sub printTemplate()
Dim num As Integer: num = 001
Dim template As Workbook
Set template = Workbooks.Open(filepath & GetVar("template" & num)) 'Complete guess at what the function is called
template.PrintOut
template.Close False
End Sub
Is there any such function that does this?
I have several Sub's in my Module. I would like to set variable that I can use in all Subs below. How to do that?
Let's say variable is a text from ThisWorkbook.Worksheets("Sheet1").Range("E1").Value and its name should be FileNameINVREQ
How to implement that in the code? I have tried:
Option Explicit
Const FileNameINVREQ As String = ThisWorkbook.Worksheets("Sheet1").Range("E1").Value
Private Sub CreateNewINVREQtoMFiles()
...
' PD Name Or title.
oPVNew.PropertyDef = 0
oPVNew.TypedValue.SetValue MFDatatypeText, FileNameINVREQ
oPVsNew.Add -1, oPVNew
...
End Sub
Private Sub CreateINVREQtoMFiles()
...
oFile.SourceFilePath = Environ("Temp") & "\" & FileNameINVREQ & ".docx"
oFile.Title = FileNameINVREQ
oFile.extension = "docx"
oFiles.Add 0, oFile
...
End Sub
A constant means it cannot be changed. For a variable, taking data from a cell, accessible from everywhere a public function without arguments would do the job:
Public Function FileNameINVREQ() As Variant
FileNameINVREQ = ThisWorkbook.Worksheets("Sheet1").Range("E1").Value
End Function
Pulling a value from a worksheet is technically not a constant (since the value could change) so you'll need to use a variable instead. However, while you can declare variables as global, you can't set them outside of a sub or function.
My suggestion would be to move both the declaration and setting the value to its own subroutine that you reference when you need to know the value.
Global FileNameINVREQ as string
Sub FileName()
FileNameINVREQ = ThisWorkbook.Worksheets("Sheet1").Range("E1").Value
End Sub
Going a step further, you could scrap it as a variable entirely and just change that FileName sub to a function! Hopefully one of these solutions works for you!
I am trying to create a code that outputs the date (e.g. 201607) contained within the workbook name (e.g. 20160701_tyo). In the following code, I specify which cell to output the value, but I always run into an error that I didn't "define my object". What am I missing?
Sub WorksheetDateName()
Dim DateName As String, OnlyDate As Long
DateName = ActiveWorkbook.Name
OnlyDate = Left(DateName.Value, 6)
ActiveWorksheet.Range("E1").Value = OnlyDate
End Sub
Also, would it be possible to perform something similar for "ActiveSheet" in addition to "ActiveWorkbook"? Thank you in advance!
For the Workbook name, you could use VBA:
ActiveSheet.Range("E1").Value = Left(ActiveWorkbook.Name, 6)
Or you could just use a formula in E1 such as:
=MID(CELL("filename"),FIND("[",CELL("filename"))+1,6)
For the Worksheet name, if you wanted the first 6 characters you could use VBA:
ActiveSheet.Range("F1").Value = Left(ActiveSheet.Name, 6)
and the equivalent formula would be:
=MID(CELL("filename"),FIND("]",CELL("filename"))+1,6)
Note: both Excel formula require that the file has been saved at least once previously to work correctly.
Looking through your code though, one way to 'fix' it would be to use Val to convert the 6 character string to a value, that can be held in the Long.
Sub WorksheetDateName()
Dim DateName As String, OnlyDate As Long
DateName = ActiveWorkbook.Name
OnlyDate = Val(Left(DateName, 6))
ActiveSheet.Range("G1").Value = OnlyDate
End Sub
You'll also note I've changed ActiveWorksheet to Activesheet - as other comments have suggested.
I have declared constants like the below in the module,
Public Const strFolderA1 = "C:\ABCD\One"
Public Const strFolderA2 = "C:\ABCD\two"
I am trying to call this in a loop,
For i = 1 To 3
strFile = Dir(strFolderA & i & "\" & filenm)
Loop
The above Dir code is wrong, but I want to call the constant based on the looping integer.
Could someone help?
Please let me know if the question is not clear.
VBA does not provide any method for concatenating a string to be used as a dynamic variable name. You could create a string constant with a delimiter then split it before use.
Option Explicit
Public Const strFolderA As String = "C:\ABCD\One|C:\ABCD\Two|C:\ABCD\Three"
Sub abcs()
Dim i As Long, fldrs As Variant
fldrs = Split(strFolderA, "|")
For i = LBound(fldrs) To UBound(fldrs)
Debug.Print fldrs(i)
Next i
End Sub