How do I edit my code to paste with a blank column between each paste? This is from a loop of each filter and pasting to another sheet. The code below works but it starts at C column when I want it to start at B.
Set shtcopy = Sheets("Summary Copying")
Set shtpaste = Sheets("Summary")
shtcopy.PivotTables
pt.TableRange1.Copy
shtpaste.Cells(10, Columns.Count).End(xlToLeft).Offset(, 2).PasteSpecial Paste:=xlPasteValues
shtpaste.Cells(10, Columns.Count).End(xlToLeft).Offset(, -4).PasteSpecial Paste:=xlPasteFormats
shtpaste.Cells.Columns.AutoFit
Option Explicit
Sub CopyPaste()
Dim pt As PivotTable, wb As Workbook, n As Long
Dim shtCopy As Worksheet, shtpaste As Worksheet
Set wb = ThisWorkbook
With wb
Set shtCopy = .Sheets("Summary Copying")
Set shtpaste = .Sheets("Summary")
End With
Set pt = shtCopy.PivotTables(1)
pt.TableRange1.Copy
With shtpaste
n = .Cells(10, .Columns.Count).End(xlToLeft).Column
If n < 2 Then
n = 2
Else
n = n + 2
End If
.Cells(10, n).PasteSpecial Paste:=xlPasteValues
.Cells(10, n).PasteSpecial Paste:=xlPasteFormats
.Cells.Columns.AutoFit
End With
End Sub
Related
I am looking to consolidate data from multiple worksheets and Workbooks with different column headers into single worksheet name (Database) using vba. Currently I have the below code that opens two workbooks and copies the sheets to the destination workbook. Then currently (Database sheet) in the destination workbook has fixed headers which are then matched with headers in all the copied sheets and then copies all the row data and pastes into Database sheet for the respective column header.
Sub CopySheetFromClosedWB()
Application.ScreenUpdating = False
Dim closedBook1 As Workbook
Dim closedBook2 As Workbook
Set closedBook1 = Workbooks.Open("C:\New folder\Exec_072021.xlsb", Password:="**********")
Set closedBook2 = Workbooks.Open("C:\New folder\Non Exec_072021.xlsb", Password:="**********")
Dim ws1 As Worksheet
For Each ws1 In closedBook1.Sheets
ws1.Copy After:=ThisWorkbook.Sheets(3)
ActiveSheet.Name = ActiveSheet.Name & "_Exec"
If ActiveSheet.AutoFilterMode Then
ActiveSheet.AutoFilterMode = False
End If
Next ws1
closedBook1.Close SaveChanges:=False
Dim ws2 As Worksheet
For Each ws2 In closedBook2.Sheets
ws2.Copy After:=ThisWorkbook.Sheets(3)
ActiveSheet.Name = ActiveSheet.Name & "_NonExec"
If ActiveSheet.AutoFilterMode Then
ActiveSheet.AutoFilterMode = False
End If
Next ws2
closedBook2.Close SaveChanges:=False
Call UpDateData
MsgBox "Database Created!!"
Application.ScreenUpdating = True
End Sub
Sub UpDateData()
Application.ScreenUpdating = False
Dim i As Long, j As Long, k As Long, n As Long, wData As Worksheet, _
Process(1 To 10) As String, iProc As Long, Dict As Object
Process(1) = "Manila_Exec"
Process(2) = "Cebu_Exec"
Process(3) = "Davao_Exec"
Process(4) = "CDO_Exec"
Process(5) = "Bacolod_Exec"
Process(6) = "Manila_NonExec"
Process(7) = "Cebu_NonExec"
Process(8) = "Davao_NonExec"
Process(9) = "CDO_NonExec"
Process(10) = "Bacolod_NonExec"
Set wData = Sheets("Database")
Set Dict = CreateObject("Scripting.Dictionary")
With wData
.UsedRange.Offset(1).Clear
For j = 1 To .Cells(1, .Columns.Count).End(xlToLeft).Column
If Len(.Cells(1, j)) > 0 Then Dict.Add LCase$(.Cells(1, j)), j
Next j
End With
i = 2
For iProc = 1 To 10
With Sheets(Process(iProc))
n = .Cells(.Rows.Count, 1).End(xlUp).Row
For j = 1 To .Cells(1, .Columns.Count).End(xlToLeft).Column
If Dict.exists(LCase$(.Cells(1, j))) Then
k = Dict(LCase$(.Cells(1, j)))
.Cells(2, j).Resize(n - 1).Copy wData.Cells(i, k).Resize(n - 1)
End If
Next j
End With
i = i + n - 1
Next iProc
Sheets("Database").Select
Selection.CurrentRegion.Select
Selection.CurrentRegion.Font.Size = 9
Selection.CurrentRegion.Font.Name = "Calibri"
Selection.CurrentRegion.Borders.LineStyle = x1None
For x = 1 To ActiveSheet.UsedRange.Columns.Count
Columns(x).EntireColumn.AutoFit
Next x
End Sub
I am trying to make a code that can eliminate the dependency of moving the sheets from multiple workbooks to destination workbook and copy values along with header names for all the matched and unmatched column headers.
Headers are in row 1 in all the worksheets.
Total rows - 50000+
Total columns - 170+
Tested, and working for me.
EDIT: made a bunch of fixes.
Sub ProcessWorkbooks()
Dim f, wsData As Worksheet, wbSrc As Workbook, map As Object
Set wsData = ThisWorkbook.Sheets("Data")
wsData.UsedRange.ClearContents 'clear any existing data
Set wbSrc = Workbooks.Open("C:\New folder\Exec_072021.xlsb", Password:="**********")
ImportData wbSrc, wsData
wbSrc.Close False
Set wbSrc = Workbooks.Open("C:\New folder\Non Exec_072021.xlsb", Password:="**********")
ImportData wbSrc, wsData
wbSrc.Close False
With wsData.Range("A1").CurrentRegion
.Font.Size = 9
.Font.Name = "Calibri"
.Borders.LineStyle = xlLineStyleNone
.EntireColumn.AutoFit
End With
End Sub
Sub ImportData(wbIn As Workbook, wsData As Worksheet)
Dim lrData As Long, lrSrc As Long, ws As Worksheet, c As Range
Dim Process, hdr, m
Process = Array("Manila", "Cebu", "Davao", "CDO", "Bacolod")
Application.ScreenUpdating = False
For Each ws In wbIn.Worksheets
If Not IsError(Application.Match(ws.Name, Process, 0)) Then 'process this sheet?
lrData = SheetLastRow(wsData) + 1
If lrData = 1 Then lrData = 2 'in case no headers yet...
lrSrc = SheetLastRow(ws)
For Each c In ws.Range("A1", ws.Cells(1, Columns.Count).End(xlToLeft)).Cells
hdr = c.Value
m = Application.Match(hdr, wsData.Rows(1), 0) 'existing column match?
If IsError(m) Then
m = Application.CountA(wsData.Rows(1))
m = IIf(m = 0, 1, m + 1)
wsData.Cells(1, m).Value = hdr 'add as new column header
End If
ws.Range(c.Offset(1), ws.Cells(lrSrc, c.Column)).Copy _
wsData.Cells(lrData, m)
Next c
End If
Next ws
End Sub
'return the last used row in a worksheet
Function SheetLastRow(ws As Worksheet) As Long
Dim f As Range
Set f = ws.Cells.Find("*", ws.Range("A1"), xlFormulas, xlPart, xlByRows, xlPrevious)
If Not f Is Nothing Then SheetLastRow = f.Row 'otherwise 0
End Function
So, I am using this macro to search by id(serial number) and then the delete the row elements for that particular row.
The code for deleting the row is:
Sub DeleteMe()
'declare the variables
Dim ID As Range, c As Range, orange As Range
Dim wb As Workbook
Set wb = ThisWorkbook
Set Fws = wb.Sheets("Data")
Set Bws = wb.Sheets("Bookings")
Dim lastrow As Long
'set the object variable
Set ID = Bws.Range("B3")
'stop screen flicker
Application.ScreenUpdating = False
lastrow = Fws.Range("A" & Rows.Count).End(xlUp).Row
Set orange = Fws.Range("A2:A" & lastrow)
'find the value in the range
For Each c In orange
If c.Value = ID.Value Then
'delete the row
c.Cells(1, 2).Clear
c.Cells(1, 3).Clear
c.Cells(1, 4).Clear
c.Cells(1, 5).Clear
c.Cells(1, 6).Clear
c.Cells(1, 7).Clear
c.Cells(1, 8).Clear
c.Cells(1, 9).Clear
c.Cells(1, 10).Clear
c.Cells(1, 11).Clear
c.Cells(1, 12).Clear
c.Cells(1, 13).Clear
c.Clear
End If
Next c
Sheet2.Select
End Sub
I am not deleting the entire row because There are values in further columns which I don't want to touch
After the code is run, my database looks like this:
What I want is to shift all the remaining rows up to fill the empty row. I also want the serial numbers to change accordingly. So in this case 7 will become 6 and 8 will become 7.
Thanks in advance!
Please try this code. It should do what you want.
Sub DeleteMe()
' 018
'declare the variables
Dim Wb As Workbook
Dim Fws As Worksheet, Bws As Worksheet
Dim DelRng As Range
Dim Id As String
Dim Rl As Long ' last row
Dim R As Long ' row counter
'set the object variables
Set Wb = ThisWorkbook
Set Fws = Wb.Sheets("Data")
Set Bws = Wb.Sheets("Bookings")
'stop screen flicker
Application.ScreenUpdating = False
Set Id = Bws.Range("B3")
With Fws
' loop through all cells from bottom to top
' because row numbers will change as you delete cells
For R = .Range("A" & .Rows.Count).End(xlUp).Row To 2 Step -1
'find the value in each row
If .Cells(R, "A").Value = Id.Value Then
Set DelRng = .Range(.Cells(R, 1), .Cells(R, 13))
DelRng.Delete Shift:=xlUp
End If
Next R
Rl = .Cells(.Rows.Count, "A").End(xlUp).Row
For R = 2 To Rl
.Cells(R, "A").Value = R - 1
Next R
End With
End Sub
Try This .. Looping upward helps to ensure all rows are covered. Because if we loop downward once we delete a row then the next row number becomes i -1
Sub DeleteMe()
'declare the variables
Dim Fws As Worksheet, Bws As Worksheet
Dim ID As Range
Dim wb As Workbook
Set wb = ThisWorkbook
Set Fws = wb.Sheets("Data")
Set Bws = wb.Sheets("Bookings")
Dim lastrow As Long
'set the object variable
Set ID = Bws.Range("B3")
'stop screen flicker
Application.ScreenUpdating = False
lastrow = Fws.Range("A" & Rows.Count).End(xlUp).Row
'find the value in the range
Fws.Select
For i = lastrow To 2 Step -1
If Fws.Cells(i, 1) = ID.Value Then
'delete the row
Fws.Range(Cells(i, 1), Cells(i, 13)).Delete Shift:=xlUp
End If
Next
With Range("A2:A" & Range("A" & Rows.Count).End(xlUp).Row)
.Formula = "=ROW() - 1"
.Value = .Value
End With
End Sub
i need to insert copied rows into another worksheet
i write this code and it doesn`t insert it, it gives me error.
Sub IsEmptyExample1()
Dim wss As Sheets
Dim ws As Worksheet
Set wss = ThisWorkbook.Worksheets
Set ws = wss("Sheet1")
wsLR = ws.Cells(Rows.Count, 1).End(xlUp).Row
For x = 1 To wsLR
Cells(x, 1).Select
If IsEmpty(ActiveCell.Value) = False Then
ThisWorkbook.Worksheets("sheet1").Rows(x).Select
Selection.Copy
Sheets("DE Portal LL").Select
Selection.Insert Shift:=xlDown
Else
End If
Next x
End Sub
I think you should read this to learn how to avoid using select. You had a few undeclared variables in your code. Your code was also copying a row and then trying to insert a new row onto a worksheet with that data. It would be better to just copy and paste to a new worksheet. Let me know if this helps:
Sub IsEmptyExample2()
Dim ws As Worksheet
Set ws = ThisWorkbook.Worksheets("Sheet1")
Dim Source As Range
Set Source = Worksheets("Sheet1").Range(("A1"), Range("A1").End(xlDown).End(xlToRight))
Dim DestRange As Range
Set DestRange = Worksheets("DE Portal LL").Range("A1")
Dim wsLR As Long
wsLR = ws.Cells(Rows.Count, 1).End(xlUp).Row
Dim x As Long
For x = 1 To wsLR
If Cells(x, 1).Value <> "" Then
Source(x, 1).Rows.EntireRow.Copy
DestRange(x, 1).PasteSpecial xlPasteAll
End If
Next x
End Sub
I may have up to 8 unique values in column D. I am looking for a code that will copy & paste each row with unique value to a new sheet.
So I may have up to 8 new sheets.
Could you help me to build the code that will do that?
This is what I have so far:
Option Explicit
Sub AddInstructorSheets()
Dim LastRow As Long, r As Long, iName As String
Dim wb As Workbook, ws As Worksheet, ts As Worksheet, nws As Worksheet
Dim i As Integer
Dim m As Integer
'set objects
Set wb = ActiveWorkbook
Set ws = ActiveSheet
Set ts = Sheets("Master")
'set last row of instructor names
LastRow = ws.Cells(ws.Rows.Count, "K").End(xlUp).Row
'add instructor sheets
On Error GoTo err
Application.ScreenUpdating = False
For r = 17 To LastRow 'assumes there is a header
iName = ws.Cells(r, 4).Value
With wb 'add new sheet
ts.Copy After:=.Sheets(.Sheets.Count) 'add template
Set nws = .Sheets(.Sheets.Count)
nws.Name = iName
Worksheets(iName).Rows("17:22").Delete
Worksheets("Master").Activate
Range(Cells(r, 2), Cells(r, 16)).Select
Selection.Copy
m = Worksheets(iName).Range("A15").End(xlDown).Row
Worksheets(iName).Cells(m + 1, 1).PasteSpecial Paste:=xlPasteValues
Application.CutCopyMode = False
End With
Next r
err:
ws.Activate
Application.ScreenUpdating = True
End Sub
The thing is that this macro is creating new sheets, which is not necessary. I only want to make following.
If you find a unique value in column D (which will have exact name as other sheet), find this sheet and paste whole row in there.
Sub CopyFromColumnD()
Dim key As Variant
Dim obj As Object
Dim i As Integer, lng As Long, j As Long
Dim sht As Worksheet, mainsht As Worksheet
Set obj = CreateObject("System.Collections.ArrayList")
Set mainsht = ActiveSheet
With mainsht
lng = .Range("D" & .Rows.Count).End(xlUp).Row
With .Range("D1", .Range("D" & lng))
For Each key In .Value
If Not obj.Contains(key) Then obj.Add key
Next
End With
End With
For i = 0 To obj.Count - 1
Set sht = Sheets.Add(After:=Sheets(Sheets.Count))
sht.Name = obj(i)
For j = 1 To lng
If mainsht.Cells(j, 4).Value = obj(i) Then
mainsht.Rows(j).EntireRow.Copy Destination:=Range("A1")
Exit For
End If
Next
Next
End Sub
Ok, I did the workaround. I have created a list of unique values in a separate sheet.
Sub copypaste()
Dim i As Integer
Dim j As Integer
LastRow = Worksheets("Master").Range("D17").End(xlDown).Row
For i = 17 To LastRow
For j = 2 To 10
Workstream = Worksheets("Database").Cells(j, 5).Value
Worksheets("Master").Activate
If Cells(i, 4) = Worksheets("Database").Cells(j, 5).Value Then
Range(Cells(i, 2), Cells(i, 16)).Select
Selection.Copy
Worksheets(Workstream).Cells(1, 1).PasteSpecial Paste:=xlPasteValues
Else
End If
Next j
Next i
End Sub
Thank you everyone for help and your time!
I am currently using the following code to copy paste data from File- "Source" to File-"Destination". It is selecting the rows till data ends in Column-1.
However, currently all the columns from A to AE are selected, but instead I want selective columns like A,F,K,AA to be selected.
I understand that the code in "wb.ActiveSheet.Range("A2:AE" & N).Copy" needs to be changed but not sure of the syntax.
Can anyone help me with this? Appreciate the help in advance.
Dim wb As Workbook
Set wb = ActiveWorkbook
Dim N As Long
Dim LastRow As Long
N = Cells(2, 1).End(xlDown).Row
wb.ActiveSheet.Range("A2:AE" & N).Copy
Set y = Workbooks.Open("C:\Desktop\Destination.xlsx")
y.Activate
y.Sheets("Data").Select
y.Sheets("Data").Activate
For Each Cell In y.Sheets("Data").Columns(1).Cells
If Len(Cell) = 0 Then Cell.Select: Exit For
Next Cell
Selection.PasteSpecial Paste:=xlPasteValues
Application.DisplayAlerts = False
ActiveWorkbook.Close True
Application.DisplayAlerts = True
Application.CutCopyMode = False
You can use the Application.Union to combine ranges from different columns (from row 2 until N).
Also, instead of looping through your y.Sheets("Data").Columns(1).Cells to find the empty Cell, you can just use LastRow = .Cells(.Rows.Count, "A").End(xlUp).Row + 1.
I added 2 With wb.Sheets("Sheet1") to fully qualify all variables and Range nested underneath.
Code
Option Explicit
Sub CopyColumns()
Dim wb As Workbook
Dim Y As Workbook
Dim N As Long
Dim LastRow As Long
Dim CopyRng As range
Application.DisplayAlerts = False
Application.ScreenUpdating = False
Set wb = ActiveWorkbook
' you need to specify the sheet, otherwise it will take the Active Sheet
With wb.Sheets("Sheet1") ' <-- modify to your sheet's name
N = .Cells(.Rows.Count, "A").End(xlUp).Row ' <-- get last row from Column "A", skips blank cells in te middle
' set the range to Columns A, F, K, AA
Set CopyRng = Application.Union(.Range("A2:A" & N), .Range("F2:F" & N), .Range("K2:K" & N), .Range("AA2:AA" & N))
End With
Set Y = Workbooks.Open("C:\Desktop\Destination.xlsx")
With Y.Sheets("Data")
LastRow = .Cells(.Rows.Count, "A").End(xlUp).Row + 1 '<-- get first empty row at Column A to paste at
CopyRng.Copy
.Range("A" & LastRow).PasteSpecial xlPasteValues
End With
Y.Close True
Application.DisplayAlerts = True
Application.ScreenUpdating = True
Application.CutCopyMode = False
End Sub