copy tab contents across different worksheets - vba

I get an extraction from SAP that usually has 40 tabs. I then need to copy their contents in other tabs across another workbook - my template. This template is made of 40 input tabs. For each input tab there is always an extracted tab which contents I will paste. I have been trying to automate this task with the following code.
Option Explicit
Sub copytabs()
Workbooks("test").Worksheets("sheet1").Range("A1:PPP999").Copy
Workbooks("test2").Worksheets("sheet1").Activate
Range("B2").Select
ActiveSheet.Paste
Workbooks("test").Worksheets("sheet3").Range("A1:PPP999").Copy
Workbooks("test2").Worksheets("sheet3").Activate
Range("B2").Select
ActiveSheet.Paste
Workbooks("test").Worksheets("sheet5").Range("A1:PPP999").Copy
Workbooks("test2").Worksheets("sheet5").Activate
Range("B2").Select
ActiveSheet.Paste
End Sub
This code does the work though very slowly. I tried to work on Array bu not luck.
Does any of you has a suggestion?
Cheers
Fabi

No need to use .Activate and .Select. They make your code slower. You may also want to see How to avoid using Select in Excel VBA macros
Also you can write the above code in a loop if the sheet names are like Sheet1, Sheet2...Sheet40
Option Explicit
Sub copytabs()
Dim wbI As Workbook, wbO As Workbook
Dim i As Long
Set wbI = Workbooks("test")
Set wbO = Workbooks("test2")
Application.ScreenUpdating = False
For i = 1 To 40 Step 2
wbI.Sheets("sheet" & i).Range("A1:PPP999").Copy _
wbO.Sheets("sheet" & i).Range("B2")
DoEvents
Next i
Application.CutCopyMode = False
Application.ScreenUpdating = True
End Sub
BTW creating a copy of workbook test and renaming it to Test2 would be much faster?
EDIT
my extraction has 40 tabs and each of them has a name. For example Praline 1617, Total Company 1617 and so on...Then I paste their contents in tabs named exactly like their original. So my template has the same tabs name of the extraction. – Fabi 1 min ago
Is this what you want?
Option Explicit
Sub copytabs()
Dim wbI As Workbook, wbO As Workbook
Dim ws As Worksheet
Set wbI = Workbooks("test")
Set wbO = Workbooks("test2")
Application.ScreenUpdating = False
For Each ws In wbI.Worksheets
ws.Range("A1:PPP999").Copy wbO.Sheets(ws.Name).Range("B2")
DoEvents
Next ws
Application.CutCopyMode = False
Application.ScreenUpdating = True
End Sub

Adjust the For loop indices to match your needs:
Sub copytabs()
For i = 1 To 11 Step 2
Workbooks("test").Worksheets("sheet" & i).Range("A1:PPP999").Copy Workbooks("test2").Worksheets("sheet" & i).Range("B2")
Next i
End Sub
This avoids using Select.

Alternatively, in case the worksheets have specific names and to improve the readability of the code, then use the following code
Sub CopyPaste()
WSName = Array("Sheet1", "Sheet3", "Sheet5")
For n = LBound(WSName) To UBound(WSName)
With Workbooks("test").Worksheets(WSName(n)).Range("A1:PPP999")
.Copy Workbooks("test2").Worksheets(WSName(n)).Range("B2")
End With
Next
End Sub

Related

How can I recode this so it can loop through specific worksheets in a workbook

I have a macro that I need to loop through specific worksheets, but I built the code through many examples I found online. So I am not quite sure where or how to set the loop and I'm also certain I would have to change the way the whole code is set up. I really have no coding knowledge at all. Meep.
Sub datatransfer()
Application.ScreenUpdating = False
Dim copySheet As Worksheet
Dim pasteSheet As Worksheet
Set copySheet = Worksheets(ActiveSheet.Name)
Set pasteSheet = Worksheets("CMICIMPORT")
copySheet.Range("A100:AA124").Copy
pasteSheet.Cells(Rows.Count, 1).End(xlUp).Offset(1, 0).PasteSpecial xlPasteValues
Application.CutCopyMode = False
Application.ScreenUpdating = True
MsgBox "Data was copied over to the CMICIMPORT tab successfully", vbInformation, ActiveSheet.Name
Range("M4").Select
With Selection.Font
.Color = -11489280
.TintAndShade = 0
End With
End Sub
I have to run the code above on each sheet that I am currently on as opposed to being able to run the Macro and it runs on all of my payroll tabs. Also my tabs are named payroll (1), payroll (2) and so forth through payroll (200) if this makes it easier to help me.
This is a quick and dirty solution, but still would work.
Start with declaring the sheets which should be looped in an Array() called specificWorksheets. If they are indeed 200, then it is a better idea to create some kind of a loop or to read them from a settings worksheets. Anyway, this is the working part:
Sub TestMe()
Dim specificWorksheets As Variant
specificWorksheets = Array("payroll (3)", "payroll (1)", "payroll (2)")
Dim wks As Worksheet
For Each wks In ThisWorkbook.Worksheets
If valueInArray(wks.Name, specificWorksheets) Then
wks.Activate
'Do your stuff, writing before...
End If
Next
End Sub
Public Function valueInArray(myValue As Variant, myArray As Variant) As Boolean
Dim cnt As Long
For cnt = LBound(myArray) To UBound(myArray)
If LCase(CStr(myValue)) = LCase(CStr(myArray(cnt))) Then
valueInArray = True
Exit Function
End If
Next cnt
End Function
At the place of the comment 'Do your stuff , copy and paste your code.
Why is this Quick and dirty? Mainly because of the using Activate and thus referring to the active worksheet. Once you realize how the for-each loop works, it is a better idea to read this - How to avoid using Select in Excel VBA - and to rewrite your code. There is a reason, why this is the second most popular topic in [vba] in StackOverflow.
Sub DataTransfer()
Dim sht As Worksheet
Application.ScreenUpdating = False
For each sht in ThisWorkbook.Worksheets
If Left(sht.Name, 7) = "payroll" Then DoIt sht
Next
Application.ScreenUpdating = True
End Sub
Sub DoIt(copySheet As Worksheet)
copySheet.Range("A100:AA124").Copy
Worksheets("CMICIMPORT").Cells(Rows.Count, 1).End(xlUp).Offset(1, 0).PasteSpecial xlPasteValues
Application.CutCopyMode = False
MsgBox "Data was copied over to the CMICIMPORT tab successfully", vbInformation, copySheet.Name
With copySheet.Range("M4").Font
.Color = -11489280
.TintAndShade = 0
End With
End Sub

Copy/Paste Macro Pasting Randomly

I am having an issue copying and pasting a drop-down data validation menu from one sheet into all selected sheets. The drop-down menu seems to paste randomly instead of pasting into sheet "B22" of the selected sheets.
Sub TEST()
Dim sht As Worksheet
Sheets("Sheet2").Range("B22").Copy
'Sheets selection should be done before running macro
Selection.Range("B22").PasteSpecial xlPasteValidation
Application.CutCopyMode = False
End Sub
Any suggestions on how to tackle this? I am having some difficulty finding the error in my code.
In case you want to work with the workbook and avoid using copy/paste..
Option Explicit
Sub Test()
Dim excel_sheet As Worksheet
Dim sht As Worksheet
Dim drop_down_value As Range
Set sht = ThisWorkbook.Sheets("Sheet2")
Set drop_down_value = sht.Range("B22")
'Sheets selection should be done before running macro
For Each excel_sheet In ThisWorkbook.Windows(1).SelectedSheets
excel_sheet.Range("B22").Value = drop_down_value.Value
Next
End Sub
Try the following, you need to loop through all selected Sheets instead of using Selection.Range:
Sub TEST()
Dim sht As Worksheet
Sheets("Sheet2").Range("B22").Copy
'Sheets selection should be done before running macro
For Each sht In ActiveWindow.SelectedSheets
sht.Range("B22").PasteSpecial xlPasteValidation
Application.CutCopyMode = True
Next
End Sub

Loop and Paste special

I'm copying values as part of one sub process and pasting value through an update button on userform.
To copy values:
Private Sub Month1_Click()
Application.DisplayAlerts = False
Application.ScreenUpdating = False
Application.AskToUpdateLinks = False
Dim wkb As Workbook
Dim wks As Worksheet
Set wkb = Workbooks.Open("Place on drive")
Set wks = wkb.Sheets("Training1")
wks.Range("Start:Finish").Copy
wkb.Close
Application.DisplayAlerts = True
Application.AskToUpdateLinks = True
Application.ScreenUpdating = True
End Sub
To paste values in current sheet:
Private Sub UpdateActuals_Click()
For i = 1 To 12
If Me.Controls("Month" & i).Value = True Then
ThisWorkbook.Sheets("2017 Actuals").Range(i+1, 5).PasteSpecial xlPasteValues
End If
Next i
End Sub
If I replace "i+1, 5" with "B5", it errors with
"PasteSpecial method of Range class failed".
I feel as if values copied in one sub process are not brought to second one, would that be correct?
Also, how do I reduce processing time given that I have 12 months (12 files) in various places that I can't change the location for...
Range usually likes a starting cell and an ending cell. I suggest since you are looking at just one cell that you change .Range to .Cells. If you really want to use a range with RC format, .Range(Cells(row1, col1), Cells(row2, col2)), if you want just one cell then you can make the two parts the same. I have run into problems before using Range and only one cell definition before, either make it .Cells for your target or fill out Range the way I have explained.. Cheers.
Dim 2017actWS AS Worksheet
Set 2017actWS = ThisWorkbook.Worksheets("2017 Actuals")
1)
2017actWS.Cells(i+1, 5).PasteSpecial xlPasteValues
-or-
2)
2017actWS.Range(2017actWS.Cells(i+1, 5), 2017actWS.Cells(i+1,5)).PasteSpecial xlPasteValues
When using Ranges excel will often throw errors if they are not the same size in a copy and paste, you can eliminate that by using a single cell as the starting target of your paste with .Cells
Also I don't see you call your function. You will want your paste close to your copy or you might find things get strange (suggestion: just after your copy).
Edited to be sure there is not worksheeet ambiguity. Thank you Scott C.
Cheers, WWC

VBA Looping Through Folder Formula Pasting Issue

I have written a macro that can successfully loop through a folder, copy and paste the information into a new workbook, and insert three formulas. I'm having problems, though, with the index functions in some macros I call not displaying correctly.
Sub LoopAllExcelFilesInFolder()
Application.ScreenUpdating = False
Dim MyFolder As String
Dim MyFile As String
MyFolder = "C:\Users\myname\Desktop\Test Files"
MyFile = Dir(MyFolder & "\*.xlsx")
'This is where my loop code starts
Do While MyFile <> ""
Workbooks.Open Filename:=MyFolder & "\" & MyFile, UpdateLinks:=0
Sheets("Report").Activate
Sheets("Report").Cells.Select
Application.CutCopyMode = False
Application.DisplayAlerts = False
Selection.Copy
ActiveWorkbook.Close True
Windows("Database Loop Test.xlsm").Activate
Sheets("PORT").Activate
Range("A1").Select
ActiveSheet.Paste
'It is successfully pasted to the desired workbook
'Here I call macros that insert sum, mid, and index functions. Sum and mid work but index doesn't
Call icvba
Call iovba
Call idvba
MyFile = Dir
Loop
End Sub
The weird thing is, when I check the index functions after I run the macro, they are all correct. Instead of showing the correct numbers, it shows up as #N/A. Here is the code for the macros I am calling. The code is the same for all three; only the worksheet is being changed.
Sub icvba()
Worksheets("COMMIT").Activate
Dim source As Worksheet
Dim detntn As Worksheet
Dim EmptyColumn As Long
Dim LastRow As Long
Set source = Sheets("vlookup")
Set detntn = Sheets("COMMIT")
LastColumn = detntn.Cells(1, detntn.Columns.Count).End(xlToLeft).Column
LastRow = Worksheets("COMMIT").Range("A:A").Rows.Count
'This if statement inputs the troublesome index function
If detntn.Range("A2") <> "" Then
EmptyColumn = LastColumn + 1
detntn.Cells(3, EmptyColumn).Formula = "=INDEX(PORT!$S$5:$S$4000,MATCH(COMMIT!$G3,PORT!$G$5:$G$4000,0))"
LastRow = ActiveSheet.UsedRange.Rows.Count
detntn.Cells(3, EmptyColumn).AutoFill destination:=detntn.Range(detntn.Cells(3, EmptyColumn), detntn.Cells(LastRow, EmptyColumn))
End If
'This if statement inputs the mid function
If detntn.Range("A2") <> "" Then
detntn.Cells(2, EmptyColumn).Formula = "=MID(PORT!$A$2,7,50)"
End If
'This if statement inputs a sum function
If detntn.Range("A2") <> "" Then
Worksheets("vlookup").Activate
ActiveSheet.Range("A1").Select
Selection.Copy
Worksheets("COMMIT").Activate
detntn.Cells(1, EmptyColumn).Select
Selection.PasteSpecial Paste:=xlAll
End If
Columns(EmptyColumn).Select
Selection.Copy
Selection.PasteSpecial Paste:=xlPasteValuesAndNumberFormats
Application.CutCopyMode = False
End Sub
Additionally, when I call the icvba, iocba, idvba macros individually, they work perfectly. It is only when I call them inside of my loop function that they stop working.
This is the first loop I have written with VBA, so I might be missing something simple. I just can't figure out where I'm going wrong. Any help would be much appreciated!
Sounds like the formulas just haven't calculated - Try putting this just before copying doing the pastespecial at the end:
Not_Calculated:
Application.Wait(Now + TimeValue("0:00:04")) if not
Application.CalculationState = xlDone then goto Not_Calculated
That basically pauses the Macro from going any further for 4 seconds to allow the calculation complete and if it still hasn't wait another 4 seconds

Copy/paste values from multiple sheets, but not all sheets, into one sheet

I am needing to copy cells B3:W400 from multiple sheets (will have varying names each time it is run) and paste values into "CombinedPlans", appending each new selection under the last. I need 3 sheets excluded from the code: IBExport, MonthlyIBs, and Combined Plans.
A lot of googling with trial and error has given me the following code, which I got to work in my "practice" workbook. Now that I have put it into my production workbook, it is no longer copying any sheets. It just skips straight to the message box. What am I doing wrong?
Sub consolidatetest()
Sheets("CombinedPlans").Select
Range("B3:W1048576").Select
Selection.ClearContents
Dim J As Integer
Dim sh As Worksheet
Const excludeSheets As String = "QBExport,MonthlyIBs,CombinedPlans"
On Error Resume Next
For Each sh In ActiveWorkbook.Worksheets
If IsError(Application.Match(sh.Name, Split(excludeSheets, ","))) Then
Application.GoTo Sheets(sh.Name).[b3]
Range("B3:W400").Select
Selection.Copy
Worksheets("CombinedPlans").Activate
Range("B1048576").End(xlUp).Offset(rowOffset:=1, columnOffset:=0).PasteSpecial xlPasteValues
End If
Next
Application.CutCopyMode = False
MsgBox "Complete!"
End Sub
This should work. If you have still problems, make sure that the Sheet CombinedPlans is indeed so named.
Sub consolidatetest()
Dim wb As Workbook
Dim sh_CombPlans As Worksheet
Set wb = ThisWorkbook
Set sh_CombPlans = wb.Sheets("CombinedPlans")
sh_CombPlans.Range("B3:W1048576").ClearContents
Dim sh As Worksheet
For Each sh In ActiveWorkbook.Worksheets
Select Case sh.Name
Case "QBExport", "MonthlyIBs", "CombinedPlans":
'Do Nothing
Case Else
sh.Range("B3:W400").Copy
sh_CombPlans.Range("B1048576").End(xlUp).Offset(1, 0).PasteSpecial xlPasteValues
End Select
Next
Application.CutCopyMode = False
MsgBox "Complete!"
End Sub