I'd like VBA to stop copy pasting my top headers with the green ribbon stating "numbers are stores as texts". Is there any way to get around it? I'm trying to copy and paste financial data from another excel sheet onto my main sheet. Here's the Code. Thank you in advance.
Sub God()
'Delete all data from the ranges
ThisWorkbook.Worksheets("10k I").Cells.Clear
ThisWorkbook.Worksheets("10k B").Cells.Clear
ThisWorkbook.Worksheets("10k C").Cells.Clear
ThisWorkbook.Worksheets("10q I").Cells.Clear
ThisWorkbook.Worksheets("10q B").Cells.Clear
ThisWorkbook.Worksheets("10q C").Cells.Clear
'Open workbook Income statement
Workbooks.Open "/Users/krabbysponge/Downloads/1.xls"
Workbooks.Open "/Users/krabbysponge/Downloads/2.xls"
Workbooks.Open "/Users/krabbysponge/Downloads/3.xls"
Workbooks.Open "/Users/krabbysponge/Downloads/4.xls"
Workbooks.Open "/Users/krabbysponge/Downloads/5.xls"
Workbooks.Open "/Users/krabbysponge/Downloads/6.xls"
'Copy range to another workbook
Workbooks("1.xls").Worksheets(1).Range("A1:M150").Copy _
ThisWorkbook.Worksheets("10k I").Range("A1")
Workbooks("2.xls").Worksheets(1).Range("A1:M150").Copy _
ThisWorkbook.Worksheets("10k B").Range("A1")
Workbooks("3.xls").Worksheets(1).Range("A1:M150").Copy _
ThisWorkbook.Worksheets("10k C").Range("A1")
Workbooks("4.xls").Worksheets(1).Range("A1:M150").Copy _
ThisWorkbook.Worksheets("10q I").Range("A1")
Workbooks("5.xls").Worksheets(1).Range("A1:M150").Copy _
ThisWorkbook.Worksheets("10q B").Range("A1")
Workbooks("6.xls").Worksheets(1).Range("A1:M150").Copy _
ThisWorkbook.Worksheets("10q C").Range("A1")
'Close workbook Income statement
Workbooks("1.xls").Close SaveChanges:=True
Workbooks("2.xls").Close SaveChanges:=True
Workbooks("3.xls").Close SaveChanges:=True
Workbooks("4.xls").Close SaveChanges:=True
Workbooks("5.xls").Close SaveChanges:=True
Workbooks("6.xls").Close SaveChanges:=True
End Sub
You don't need to copy - but can write the value direct to the target sheet.
This has two advantages:
you don't use the clipboard
therefore it is much faster
According to "Don't repeat yourself" (DRY) you can put everything in a for-loop - and configuring your files in an array. In case there are changes to this setting it is much easier to adapt the code.
Public Sub copyData()
Dim arrConfig(1, 2) As String
'Target sheetname | Source filename
arrConfig(0, 0) = "10k I": arrConfig(1, 0) = "1.xls"
arrConfig(0, 1) = "10k B": arrConfig(1, 1) = "2.xls"
arrConfig(0, 2) = "10k C": arrConfig(1, 2) = "3.xls"
'...
'arrconfig(0,6) = ...
Const pathDownloads As String = "/Users/krabbysponge/Downloads/"
Const AddressToCopy As String = "A1:M150"
Dim i As Long, wbSource As Workbook, wsSource As Worksheet, wsTarget As Worksheet
For i = 0 To UBound(arrConfig, 2)
Set wsTarget = ThisWorkbook.Worksheets(arrConfig(0, i))
wsTarget.Cells.Clear
Set wbSource = Workbooks.Open(pathDownloads & arrConfig(1, i))
Set wsSource = wbSource.Worksheets(1)
'This is the part where the data are written from one range to another (values only without formatting)
wsTarget.Range(AddressToCopy).Value = wsSource.Range(AddressToCopy).Value
wbSource.Close savechanges:=True
Next
End Sub
Related
I am looking for a code to search a directory for specific file names with a changing number at the end of the name (File_1.xls, File_2.xls, File_3.xls, etc.) and stack the data within the reports on top of eachother without headers into a tab but if a File_Amend.xls file exists then it will only copy the data from that file and paste it into it's own tab. The only changing part of the File_ is 1,2,3, etc. or Amend. Everything ends in .xls
I've gotten this far:
Sub SaveFile()
Dim wb As Workbook: Set wb = ThisWorkbook
Dim ws As Worksheet
Dim File As String
Dim wsCopy As Worksheet
Dim wsCopy2 As Worksheet
Dim wsCopy3 As Worksheet
Dim wsPaste As Worksheet
' For this part I am looking to have the file name constant as "File_" and then have the code search for files with the numbers 1,2,3,4, etc. instead of hardcoding in the file name
File = "L:\Main\Code\"
Set wsCopy = File & wb.Sheets("Main").Range("C6") 'this value is "File 1.xls"
Workbooks.Open Filename:=wsCopy, ReadOnly:=True
Set wsCopy2 = File & wb.Sheets("Main").Range("C7") 'this value is "File 2.xls"
Workbooks.Open Filename:=wsCopy2, ReadOnly:=True
Set wsCopy3 = File & wb.Sheets("Main").Range ("C8") 'this value is "File Amend.xls"
Workbooks.Open Filename:=wsCopy3, ReadOnly:=True
Set wb = Workbooks.Add
Set wsPaste = wb.Sheets(1)
If Dir(wsCopy) = True Then
wsCopy.Range ("A:I").Copy
wsPaste.Cells.PasteSpecial Paste:=xlPasteValues
If Dir(wsCopy2) = True Then
wsCopy2.UsedRange.Offset(1,0).SpecialCells(xlCellTypeVisible).Copy
wsPaste.Cells (Rows.Count, "A").End(x1Up).Offset (1, 0).PasteSpecial Paste: xlPasteValues
If Dir(wsCopy3) = True Then
wsPaste.Cells.ClearContents
wsCopy3.Range("A:I").Copy
wsPaste.Range("Al").PasteSpecial Paste:=xlPasteValues
End Sub
For searching filenames with different numbers, you can use different constant "File", and FOR loop.
Special check for File_Amend.xls can be put before the above code, all like this:
If Dir ("L:\Main\Code\File_Amend.xls" = True then
...
Else
File = "L:\Main\Code\File_"
For i = 1 to 99
wsCopy = File & i & ".xls"
...
Next i
End if
I am fairly new at using VBA to manipulate data in Excel. I am trying to build about 800 bills of materials from data I have extracted from an old system we are replacing.
I have an Excel workbook with multiple sheets with a table on each sheet. What I need to do is work through every "ParentID" in one sheet and save each unique "Parent ID" and "ChildID" to a new workbook titled with the ParentID. Then lookup each unique "ChildID" in another worksheet and save data from this worksheet to the new workbook for each unique "ChildID".
I found the below VBA code and have been working on changing things to work for me as I think this will get me at least part way there but I am having trouble getting all of the Template values replaced with my values due to lack of knowlege on syntax and VBA code.
If someone could help me identify what I need to replace to get at least this code working I think I would be well on my way.
Thanks!
Option Explicit
Sub ExportData()
'Declare variables
Dim ArrayItem As Long
Dim tblUsedIn As Worksheet
Dim ArrayOfUniqueValues As Variant
Dim SavePath As String
Dim ColumnHeadingInt As Long
Dim ColumnHeadingStr As String
Dim rng As Range
'Set the worksheet to
Set tblUsedIn = Sheets("tblUsedIn")
'Set the save path for the files created
SavePath = Range("File Save Location")
'Set variables for the column we want to separate data based on
ColumnHeadingInt = WorksheetFunction.Match(Range("ParentID").Value, Range("Data[#Headers]"), 0)
ColumnHeadingStr = "Data[[#All],[" & Range("ParentID").Value & "]]"
'Turn off screen updating to save runtime
Application.ScreenUpdating = False
'Create a temporary list of unique values from the column we want to
'separate our data based on
Range(ColumnHeadingStr & "").AdvancedFilter Action:=xlFilterCopy, _
CopyToRange:=Range("UniqueValues"), Unique:=True
'Sort our temporary list of unique values
tblUsedIn.Range("UniqueValues").EntireColumn.Sort Key1:=tblUsedIn.Range("UniqueValues").Offset(1, 0), _
Order1:=xlAscending, Header:=xlYes, OrderCustom:=1, MatchCase:=False, _
Orientation:=xlTopToBottom, DataOption1:=xlSortNormal
'Add unique field values into an array
'ArrayOfUniqueValues = Application.WorksheetFunction.Transpose(tblUsedIn.Range("IV2:IV" & RotblUsedIn.Count).SpecialCells(xlCellTypeConstants))
ArrayOfUniqueValues = Application.WorksheetFunction.Transpose(tblUsedIn.Range("UniqueValues").EntireColumn.SpecialCells(xlCellTypeConstants))
'Delete the temporary values
tblUsedIn.Range("UniqueValues").EntireColumn.Clear
'Loop through our array of unique field values, copy paste into new workbooks and save
For ArrayItem = 1 To UBound(ArrayOfUniqueValues)
tblUsedIn.ListObjects("Data").Range.AutoFilter Field:=ColumnHeadingInt, Criteria1:=ArrayOfUniqueValues(ArrayItem)
tblUsedIn.Range("Data[#All]").SpecialCells(xlCellTypeVisible).Copy
Workbooks.Add
Range("A1").PasteSpecial xlPasteAll
ActiveWorkbook.SaveAs SavePath & ArrayOfUniqueValues(ArrayItem) & Format(Now(), " YYYY-MM-DD hhmmss") & ".xlsx", 51
ActiveWorkbook.Close False
tblUsedIn.ListObjects("Data").Range.AutoFilter Field:=ColumnHeadingInt
Next ArrayItem
tblUsedIn.AutoFilterMode = False
MsgBox "Finished exporting!"
Application.ScreenUpdating = True
End Sub
struggling to copy a worksheet from source book to destination book.
I've tried 4 different codes found on SO, but running into different errors all the time.
Either: "Copy method failed", "No such interface found", "Exception"- at the copy function.
I know that there are a lot of links and websites referring to the copy method, but i've tried them all and still no luck.
Option Strict = Off
Option Explicit = On
Excel 2016
VS 2019
Sourceworkbook has formatting in and merged cells. Needing the formatting included in the copy method, because I'll be using the new workbooks as back-ups or copies for printing. The sourceworkbook has a template on one of the sheets named "TempPage".
Code:
xlApp1 = New Excel.Application
xlWorkBook1 = xlApp1.Workbooks.Add
'xlWorkSheet1 = CType(xlWorkBook1.Sheets.Add(), Excel.Worksheet)
xlWorkSheet = CType(xlWorkBook.Sheets("TempPage"), Excel.Worksheet) 'Source
xlWorkSheet1 = CType(xlWorkBook1.Sheets("Sheet1"), Excel.Worksheet) 'Destination
'Tried this code
'Dim rngSource As Excel.Range, rngTarget As Excel.Range, targetRow As Long
'rngSource = xlWorkBook.Sheets("TempPage").UsedRange
'With xlWorkBook.Sheets("TempPage")
'targetRow = .UsedRange.SpecialCells(XlCellType.xlCellTypeLastCell).Row + 1
'rngTarget = .cells(targetRow, rngSource.Column)
'End With
'rngSource.Copy(rngTarget)
'Tried this code
'Dim sourceWorkSheet As Excel.Worksheet
'sourceWorkSheet = xlWorkBook.Sheets("TempPage")
'//Copies the source worksheet to the destination workbook, places it after the last
'//sheet in the destination workbook.
'sourceWorkSheet.Copy(, xlWorkBook1.Sheets(xlWorkBook1.Sheets.Count))
'Tried this
'xlWorkSheet.Copy(, xlWorkBook1.Sheets(xlWorkBook1.Sheets.Count))
'tried this
'xlWorkSheet1.Range("A1:I46").Value = xlWorkSheet.Range("A1:I46").Value
'xlWorkSheet.Application.Goto(xlWorkSheet.Range("A1:I46"), True)
'xlWorkSheet.Range("A1:I46").Select()
'xlWorkSheet.Range("A1:I46").Copy()
'xlWorkSheet1.PasteSpecial(Excel.XlPasteType.xlPasteAll,
'Excel.XlPasteSpecialOperation.xlPasteSpecialOperationNone, False, False)
'Tried this
'xlWorkSheet.Range("A1:I46").Copy(xlWorkSheet1.Range("A1:I46"))
'xlWorkSheet1.PasteSpecial(Excel.XlPasteType.xlPasteFormats)
xlWorkBook1.SaveAs(BTPath & "\" & xlWorkSheet.Range("B3").Value & ".xls", Excel.XlFileFormat.xlExcel5) 'save the receipt as the ticket number
If RadioButton3.Checked = True Then
'unpaid - send copy to unpaid folder
xlWorkBook1.SaveAs(UnpaidPath & "\" & xlWorkSheet.Range("B3").Value & ".xls", Excel.XlFileFormat.xlExcel5)
ElseIf RadioButton4.Checked = True Then
End If
I need help with the copying method please.
After a bit more research, found a way to save the worksheet from the source book. Closing the book and reopening the source book for continued usage. Only problem i'm now running into, is that the formulas are still being copied as well and some cells aren't in the same format(bold, merged, size) but found a link on SO - Save values (not formulae) from a sheet to a new workbook?
New code:
'save first
xlWorkBook.Save() 'Save the workbook
Dim newpath As String = BTPath & "\" & xlWorkSheet.Range("B3").Value & ".xls"
xlWorkSheet = CType(xlWorkBook.Sheets("TempPage"), Excel.Worksheet)
xlWorkSheet.Copy()
xlWorkSheet.SaveAs(newpath, Excel.XlFileFormat.xlExcel5)
If RadioButton3.Checked = True Then
'unpaid - send copy to unpaid folder
xlWorkBook.SaveAs(BTPath & "\" & xlWorkSheet.Range("B3").Value & ".xls")
End If
'Close the file and reopen the database file
xlWorkBook.Save() 'Save the workbook
xlWorkBook.Close() 'Close workbook
If xlApp Is Nothing Then
'do nothing
Else
xlApp.Quit() 'Quit the application
End If
GC.Collect()
GC.WaitForPendingFinalizers()
System.Threading.Thread.Sleep(500)
GC.Collect()
GC.WaitForPendingFinalizers()
System.Threading.Thread.Sleep(500)
'reopen
xlApp = New Excel.Application
xlWorkBook = xlApp.Workbooks.Open(filepath)
'clear the sheet
xlWorkSheet = CType(xlWorkBook.Sheets("TempPage"), Excel.Worksheet)
xlWorkSheet.Range("D45").Value = ""
xlWorkSheet.Range("B3").Value = ""
xlWorkSheet.Range("B10").Value = ""
xlWorkSheet.Range("F10").Value = ""
xlWorkSheet.Range("F12").Value = ""
xlWorkSheet.Range("B11").Value = ""
xlWorkSheet.Range("F11").Value = ""
xlWorkSheet.Range("I10").Value = ""
xlWorkSheet.Range("A14:H10").Value = ""
'save but don't close
xlWorkBook.Save() 'Save the workbook
I want to insert data from source files in my excel model by opening the files and copying and pasting the values. I am just updating the values and not inserting formulas, formats or images etc.
The macro works fine and the inputs are pasted in my excel model. The last command is: ActiveWorkbook.Save
However, sometimes the macro cannot save the file (and I cannot see a regularity here - sometimes it works, sometimes it doesn't) and it displays the error message: "Errors were detected while saving. Microsoft Excel may be able to save the file by removing or repairing some features. To make the repairs in a new file, click continue. To cancel saving the file, click cancel."
Does anyone have an idea on how to fix this error? I am also posting the full code below. Thanks a lot in advance!
' Definitions
Dim i As Integer
Dim mapping_sheet, Worksheet_MVP, Dateiname_Input, Name_Worksheet_Input, Pfad_Input, Pfad_Datei, Zelle, Text As String
' Workbooks
Dim MVP, Auszug As Workbook
Pfad_Input = ActiveSheet.Range("B7").Value
Set MVP = ActiveWorkbook
Sheets("Automatisierung Datenupdate").Activate
Workbooks(MVP.Name).Application.Calculation = xlCalculationManual
Workbooks(MVP.Name).Application.CalculateBeforeSave = False
' 1. Updating Macro
' Copy Pasting Data
If ActiveSheet.Range("E11").Value = "Ja" Then
Dateiname_Input = ActiveSheet.Range("M11").Value
Name_Worksheet_Input = ActiveSheet.Range("D11").Value
Worksheet_MVP = ActiveSheet.Range("B11").Value
Pfad_Datei = Pfad_Input & "\" & Dateiname_Input
Sheets(Worksheet_MVP).Activate
Range("B6:ZZ300").Select
Selection.ClearContents
Set Auszug = Workbooks.Open(Filename:=Pfad_Datei)
Workbooks(Auszug.Name).Activate
Sheets(Name_Worksheet_Input).Activate
Range("A4:ZY298").Select
Selection.Copy
Workbooks(MVP.Name).Activate
Sheets(Worksheet_MVP).Activate
Range("B6").Select
Selection.PasteSpecial Paste:=xlPasteValues
' Close and Save
Workbooks(Auszug.Name).Activate
ActiveSheet.Range("A1").Copy
Workbooks(Auszug.Name).Close savechanges:=False
Workbooks(MVP.Name).Activate
Sheets("Automatisierung Datenupdate").Activate
Range("M11").Select
Selection.Copy
Range("C11").Select
Selection.PasteSpecial Paste:=xlPasteValues
End If
' Save
Sheets("Automatisierung Datenupdate").Activate
Application.ScreenUpdating = True
ActiveWorkbook.Save
End Sub
You mix up the concepts in your code which probably leads to the unexpected/irregular errors.
If you don't specify a data type (or object type) when you dim, the variable is Variant by default. e.g. "Dim MVP" is the same as "Dim MVP as variant"
You do assign your workbooks/worksheets to a variable but don't use the magic. Once set you can just refer to the workbook by referencing the varName.
Although variables are very powerfull, when you just want to use cell values it's better to store these in memory (e.g. an array)
Hereunder an alternative approach, only using the named workbooks/worksheets and minimising the interactions with the sheet by using arrays:
Sub ceci()
'dim vars to specific datatype
Dim wb As Workbook, sh As Worksheet, arr
Set wb = ThisWorkbook
Set sh = wb.Sheets("Automatisierung Datenupdate")
'To minimize the interactions with the sheet we store the data in memory, an array
'here we can access each cell by referencing our array(<rowCounter>, <columnCounter>
'e.g. arr(j,i) => if j = 1 and i = 1 we'll have the values of Cell A1
'we can dump these values anywhere in the activesheet, other sheet, other workbook, ..
Dim sh2 As Worksheet, wb2 As Workbook
arr = sh.Range("A1").CurrentRegion.Value2 'assuming you have data as of A1 we store all in the array, you can fine tune if needed though
If arr(11, 5) = "ja" Then 'E11
'source wb
Set sh2 = wb.Sheets(arr(11, 2)) 'b11
sh2.Range("B6:ZZ300").ClearContents
'wb2 - by specifically naming the workbooks and sheets we avoid unexpected errors
Dim sh3 As Worksheet, arr2, Pfad_Datei As String: Pfad_Datei = wb.Path & "\" & arr(11, 13) 'arr(7, 2) & "\" & arr(11, 13) 'b7 & m11
Set wb2 = Workbooks.Open(Filename:=Pfad_Datei)
Set sh3 = wb2.Sheets(arr(11, 4)) 'd11
arr2 = sh3.Range("A4:ZY298").Value2
sh2.Range(sh2.Cells(6, 2), sh2.Cells(UBound(arr2), UBound(arr2, 2))).Value2 = arr2 'dumb to sheet
'wb1
sh.Range("c11").Value = arr(11, 13) 'm11
End If
wb.Save
End Sub
I would like to save file in a "CONSOLIDATE FOLDER". But the file path should depend on staff working number ID (00639) where they input it in the "TEMPLATE" worksheet cell "N3". And in case staff forgot to input their working ID, there'll be a pop up box telling them to fill in their ID.
Any help really appreciated.
Sub MergeFile ()
Dim WB As Workbook
Dim WS as Worksheet
Dim FileName as String
Dim FilePath as String
Set WB = Workbook.Add
FilePath = "C:\Users\KGA00639\Desktop\CONSOLIDATE FOLDER"
FileName = ThisWorkbook.Worksheets("TEMPLATE").Range("L15").Value
For Each WS in ThisWorkbook.Worksheets
If WS.Name <> "TEMPLATE" Then
WS.Copy before:=WB.Sheets(1)
End if
If FileName = "" Then
FileName = InputBox ("You did not name the workbook" & vbCrLf & _
"Please write the name and press OK.:,"Setting the workbook name")
If FileName = "" Then Exit sub
ThisWorkbook.Worksheets("TEMPLATE").Range("L15").Value = FileName
End If
Next
ActiveWorkbook.SaveAs FileName:=FilePath & "\" & FileName
MsgBox ("Done"!)
ActiveWorkbook.Close
End Sub
This solution should come rather close to what you want. Please take a look.
Sub MergeFile()
' 056
Dim Wb As Workbook
Dim Ws As Worksheet
Dim FileName As String
Dim FilePath As String
Dim UserID As String
With ThisWorkbook.Worksheets("TEMPLATE")
UserID = .Cells(1, "A").Value ' change address to suit
FileName = .Range("L15").Value
If Left(UserID, 2) <> "ID" Then
MsgBox "You must enter your valid user ID in" & vbCr & _
"cell A1 of the 'Template' tab." & vbCr & _
"This program will now be terminated.", _
vbInformation, "Incomplete preparation"
.Activate
.Cells(1, "A").Select ' change to match above
Exit Sub
End If
End With
Application.ScreenUpdating = False
' use the UserID variable in whichever way you wish
FilePath = Environ("UserProfile") & "\" & UserID & "\Desktop\CONSOLIDATE FOLDER"
Set Wb = Workbooks.Add
For Each Ws In ThisWorkbook.Worksheets
If Ws.Name <> "TEMPLATE" Then
Ws.Copy Before:=Wb.Sheets(1)
End If
Next Ws
Wb.SaveAs FilePath & FileName, xlOpenXMLWorkbook
Application.ScreenUpdating = True
End Sub
You didn't specify where on the 'Template' tab the user ID would be found. The above code looks for it in cell A1. That cell is mentioned in 3 locations in the code (once in the message text). Please modify the code to match your facts.
You also didn't say where the UserID should appear in the FilePath. I placed it before the Desktop. I'm sure you will know how to amend that bit of code to suit you better.
When saving the workbook my code specifies an xlsx format. If this isn't what you want change the file format constant in the SaveAs line. I didn't think it a good idea to specify the extension in the 'Template'. You may like to move it to the code.
Finally, you didn't specify the next step after creation of the new workbook. So the code ends in the middle of nowhere. Excel made the new workbook the active one but you may like to close it, or ThisWorkbook, and determine what to do with the blank worksheet(s) still contained in the new book. There are a lot of lose ends still to tidy up. Good luck!