Use VBA to paste values from one table to another - vba

I have the following VBA code that takes a single row from Sheet "Tabled data", copies the data, then pastes the data into the next available row in Sheet "Running list". However the original row has formulas and I need the values to paste, not the formulas. I've seen numerous ways to do it with Range.PasteSpecial but this code didn't use Range and I'm not sure how to incorporate it.
Note: I modified this code from here: http://msdn.microsoft.com/en-us/library/office/ff837760(v=office.15).aspx. It originally had an IF statement to match content in a cell then paste it in a certain sheet according to the content in the cell. I only had one sheet to copy to and didn't need the IF. I don't really need to find the last row of data to copy either as it will only ever be one row with range of A2:N2. But if I take out the FinalRow section and the For and replace with Range("A2:N2") it doesn't work so I left those in.
Any guidance on how to add in the PasteValues property without making this more complicated? I'm also open to simplification of the For or FinalRow variable such as using Range. I'm only sort of familiar with VBA, having done a few things with it, but usually after much searching and modifying code.
Public Sub CopyData()
Sheets("Tabled data").Select
' Find the last row of data
FinalRow = Cells(Rows.Count, 1).End(xlUp).Row
' Loop through each row
For x = 2 To FinalRow
ThisValue = Cells(x, 1).Value
Cells(x, 1).Resize(1, 14).Copy
Sheets("Running list").Select
NextRow = Cells(Rows.Count, 1).End(xlUp).Row + 1
Cells(NextRow, 1).Select
ActiveSheet.Paste
Sheets("Tabled data").Select
Next x
End Sub

Hopefully we can actually make this more simple.
Public Sub CopyRows()
Sheets("Sheet1").UsedRange.Copy
lastrow = ActiveSheet.Cells(Rows.Count, 1).End(xlUp).Row
'check if the last cell found is empty
If IsEmpty(ActiveSheet.Cells(lastrow, 1)) = True Then
'if it is empty, then we should fill it
nextrow = lastrow
Else
'if it is not empty, then we should not overwrite it
nextrow = lastrow + 1
End If
ActiveSheet.Cells(nextrow, 1).Select
ActiveSheet.Paste
End Sub
edit: I expanded it a little so that there won't be a blank line at the top

I found a working solution. I recorded a macro to get the paste special in there and added the extra code to find the next empty row:
Sub Save_Results()
' Save_Results Macro
Sheets("Summary").Select 'renamed sheets for clarification, this was 'Tabled data'
'copy the row
Range("Table1[Dataset Name]").Select
Range(Selection, Selection.End(xlToRight)).Select
Selection.Copy
' paste values into the next empty row
Sheets("Assessment Results").Select
Range("A2").Select
NextRow = Cells(Rows.Count, 1).End(xlUp).Row + 1
Cells(NextRow, 1).Select
Selection.PasteSpecial Paste:=xlPasteValues, Operation:=xlNone, SkipBlanks _
:=False, Transpose:=False
' Return to main sheet
Sheets("Data Assessment Tool").Select
End Sub

Just copy the data all at once, no need to do it a row at a time.
Sub CopyData()
With ThisWorkbook.Sheets("Tabled data")
Dim sourceRange As Range
Set sourceRange = .Range(.Cells(2, 1), .Cells(getLastRow(.Range("A1").Parent), 14))
End With
With ThisWorkbook.Sheets("Running list")
Dim pasteRow As Long
Dim pasteRange As Range
pasteRow = getLastRow(.Range("A1").Parent) + 1
Set pasteRange = .Range(.Cells(pasteRow, 1), .Cells(pasteRow + sourceRange.Rows.Count, 14))
End With
pasteRange.Value = sourceRange.Value
End Sub
Function getLastRow(ws As Worksheet, Optional colNum As Long = 1) As Long
getLastRow = ws.Cells(ws.Rows.Count, colNum).End(xlUp).Row
End Function

Private Sub Load_Click()
Call ImportInfo
End Sub
Sub ImportInfo()
Dim FileName As String
Dim WS1 As Worksheet
Dim WS2 As Worksheet
Dim ActiveListWB As Workbook
Dim check As Integer
'Application.ScreenUpdating = False
Set WS2 = ActiveWorkbook.Sheets("KE_RAW")
confirm = MsgBox("Select (.xlsx) Excel file for Data transfer." & vbNewLine & "Please ensure the sheets are named Sort List, Second and Third.", vbOKCancel)
If confirm = 1 Then
FileName = Application.GetOpenFilename(FileFilter:="Excel Files (*.xls*),*.xls*", _
Title:="Select Active List to Import", MultiSelect:=False)
If FileName = "False" Then
MsgBox "Import procedure was canceled"
Exit Sub
Else
Call CleanRaw
Set ActiveListWB = Workbooks.Open(FileName)
End If
Set WS1 = ActiveListWB.Sheets("Sort List")
WS1.UsedRange.Copy 'WS2.Range("A1")
' WS2.Range("A1").Select
WS2.UsedRange.PasteSpecial Paste:=xlPasteValues, Operation:=xlNone, SkipBlanks _
:=False, Transpose:=False
'WS2.Range ("A1")
ActiveWorkbook.Close False
'Call ClearFormulas
' Call RefreshAllPivotTables
Sheets("Key Entry Data").Select
'Sheets("Raw").Visible = False
'Application.ScreenUpdating = True
MsgBox "Data has been imported to workbook"
Else
MsgBox "Import procedure was canceled"
End If
Application.ScreenUpdating = True
End Sub
Sub CleanRaw()
Sheets("KE_RAW").Visible = True
Sheets("KE_RAW").Activate
ActiveSheet.Cells.Select
Selection.ClearContents
End Sub

Related

Copy and paste rows from one to another worksheet VBA

I know already a few people had that problem but their solutions did not help me. I am pretty new to VBA and I want to copy a row if the respective first cell is not empty to another file and iterate as long as the data is.
So far so good. My code runs the first time and actually works (for one line). But then the macro does not open the file again and spits out an error. If I want to manually open the target file it says: "Removed Feature: Data Validation from /xl/worksheets/sheet2.xml part" (and I think this is the reason why it does not iterate further). Do you have any idea what I can do?
Sub transferData()
Dim LastRow As Long, i As Integer, erow As Long
LastRow = ActiveSheet.Range("BC" & Rows.Count).End(xlUp).Row
For i = 3 To LastRow
If IsEmpty(Cells(i, 63).Value) = False Then
Range(Cells(i, 55), Cells(i, 63)).Select
Selection.Copy
Workbooks.Open Filename:="PATH.xlsx"
Worksheets("NewProjects").Select
erow = ActiveSheet.Cells(Rows.Count, 1).End(xlUp).Offset(1, 0).Row
ActiveSheet.Cells(erow, 1).Select
ActiveSheet.PasteSpecial
ActiveSheet.Sort.SortFields.Clear
ActiveWorkbook.Save
ActiveWorkbook.Close SaveChanges:=False
Application.CutCopyMode = False
End If
Next i
End Sub
Data Validation for the file is corrupt (dropdown lists) - either delete Data Validation, or fix it
Once the file is fixed, the code bellow will copy the data without opening the destination file multiple times. It AutoFilters current sheet for empty values in column BK (63), and copies all visible rows, from columns BC to BK, to the end of the new file (starting at first unused cell in column A)
Option Explicit
Public Sub TransferData()
Const OLD_COL1 = "BC"
Const OLD_COL2 = "BK"
Const NEW_COL1 = "A"
Dim oldWb As Workbook, oldWs As Worksheet, oldLR As Long
Dim newWb As Workbook, newWs As Worksheet, newLR As Long
On Error Resume Next 'Expected errors: new file not found, new sheet name not found
Set oldWb = ThisWorkbook
Set oldWs = ActiveSheet 'Or: Set oldWs = oldWb.Worksheets("Sheet2")
oldLR = oldWs.Cells(oldWs.Rows.Count, OLD_COL1).End(xlUp).Row
Application.ScreenUpdating = False
Set newWb = Workbooks.Open(Filename:="PATH.xlsx")
Set newWs = newWb.Worksheets("NewProjects")
If Not newWs Is Nothing Then
newLR = newWs.Cells(oldWs.Rows.Count, NEW_COL1).End(xlUp).Row
With oldWs.Range(oldWs.Cells(2, OLD_COL2), oldWs.Cells(oldLR, OLD_COL2))
.AutoFilter Field:=1, Criteria1:="<>"
If .SpecialCells(xlCellTypeVisible).Cells.Count > 2 Then
oldWs.Range(oldWs.Cells(3, OLD_COL1), oldWs.Cells(oldLR, OLD_COL2)).Copy
newWs.Cells(newLR + 1, NEW_COL1).PasteSpecial
Application.CutCopyMode = False
newWs.Sort.SortFields.Clear
newWb.Close SaveChanges:=True
Else
newWb.Close SaveChanges:=False
End If
.AutoFilter
End With
End If
Application.ScreenUpdating = True
End Sub

Filtering a column based on a value and copying the value from the corresponding value

This is a screenshot of my excel doc.
I want to apply filters based on values: Bimbo Mexico, Bimbo Canada and copy and paste the values(from column A & B) in a new sheet. I want to do this using macro as I am building a template for a client. Is there a way to do this? I know it can be done manually using filters manually but I want it to be based on a macro
I want the output like this:
I used recording macro and this is the macro I got,
Sub RecordedMacro()
'
' RecordedMacro Macro
'
' Keyboard Shortcut: Ctrl+l
'
Sheets("report").Select
Range("C1").Select
ActiveSheet.Range("$A$1:$S$1001").AutoFilter Field:=3, Criteria1:="Barcel"
Columns("L:L").Select
Selection.Copy
Sheets("SkuRounds").Select
Columns("S:S").Select
ActiveSheet.Paste
Sheets("report").Select
ActiveSheet.Range("$A$1:$S$1001").AutoFilter Field:=3, Criteria1:= _
"Bimbo Canada"
Columns("L:L").Select
Application.CutCopyMode = False
Selection.Copy
Sheets("SkuRounds").Select
Columns("T:T").Select
ActiveSheet.Paste
Sheets("report").Select
ActiveSheet.Range("$A$1:$S$1001").AutoFilter Field:=3, Criteria1:= _
"Bimbo Latin Centro"
Columns("L:L").Select
Application.CutCopyMode = False
Selection.Copy
Sheets("SkuRounds").Select
Columns("U:U").Select
ActiveSheet.Paste
Sheets("report").Select
ActiveSheet.Range("$A$1:$S$1001").AutoFilter Field:=3, Criteria1:= _
"Bimbo México"
Columns("L:L").Select
Application.CutCopyMode = False
Selection.Copy
Sheets("SkuRounds").Select
Columns("V:V").Select
ActiveSheet.Paste
End Sub
I am copying data from sheet(report) to sheet(skurounds)
Give this a try:
Sub tgr()
Dim wb As Workbook
Dim wsReport As Worksheet
Dim wsSKU As Worksheet
Dim dictUnqCompanies As Object
Dim aCompanies As Variant
Dim vCompany As Variant
Dim lDestCol As Long
Set wb = ActiveWorkbook
Set wsReport = wb.Sheets("report")
Set wsSKU = wb.Sheets("skurounds")
Set dictUnqCompanies = CreateObject("Scripting.Dictionary")
lDestCol = wsSKU.Columns("S").Column
'Clear previous results
wsSKU.Range(wsSKU.Cells(1, "S"), wsSKU.Cells(1, wsSKU.Columns.Count)).EntireColumn.Clear
With wsReport.Range("C2", wsReport.Cells(wsReport.Rows.Count, "C").End(xlUp))
If .Row < 2 Then Exit Sub 'No data
If .Rows.Count = 1 Then
'Only 1 row of data
wsSKU.Cells(1, lDestCol).Value = .Value
.Parent.Cells(.Row, "L").Copy wsSKU.Cells(2, lDestCol)
Exit Sub
Else
aCompanies = .Value
End If
End With
For Each vCompany In aCompanies
If Not dictUnqCompanies.exists(vCompany) Then
dictUnqCompanies.Add vCompany, vCompany
With wsReport.Range("C1", wsReport.Cells(wsReport.Rows.Count, "C").End(xlUp))
.AutoFilter 1, vCompany
wsSKU.Cells(1, lDestCol).Value = vCompany
Intersect(.Parent.Columns("L"), .Offset(1).EntireRow).Copy wsSKU.Cells(2, lDestCol)
lDestCol = lDestCol + 1
.AutoFilter
End With
End If
Next vCompany
End Sub

Excel VBA copy from one sheet to another wb doesnt overwrite data

I use vba to import data from one wb to another - but it seems like the data is not overwriten.
ex.
wb 1 cell A2 contains the number "2" and is copied to wb 2 cell A2.
But if I delete cell A2 from wb 2, and run the vba again - there is no data entered in wb 2 cell A2...
Can anyone see why this is?
Regards
Brian
Sorry forgot to add code :o)
Sub GetData()
Dim strWhereToCopy As String, strStartCellColName As String
Dim strListSheet As String
Application.ScreenUpdating = False
strListSheet = "List"
On Error GoTo ErrH
Sheets(strListSheet).Select
Range("B2").Select
'this is the main loop, we will open the files one by one and copy their data into the masterdata sheet
Set currentWB = ActiveWorkbook
Do While ActiveCell.Value <> ""
strFileName = ActiveCell.Offset(0, 1) & ActiveCell.Value
strCopyRange = ActiveCell.Offset(0, 2) & ":" & ActiveCell.Offset(0, 3)
strWhereToCopy = ActiveCell.Offset(0, 4).Value
strStartCellColName = Mid(ActiveCell.Offset(0, 5), 2, 1)
Application.Workbooks.Open strFileName, UpdateLinks:=False, ReadOnly:=True
Set dataWB = ActiveWorkbook
Range(strCopyRange).Select
Selection.Copy
currentWB.Activate
Sheets(strWhereToCopy).Select
lastRow = LastRowInOneColumn(strStartCellColName)
Cells(lastRow + 1, 1).Select
Selection.PasteSpecial xlPasteValues, xlPasteSpecialOperationNone
Selection.PasteSpecial Paste:=xlPasteFormats, Operation:=xlNone, SkipBlanks:=False, Transpose:=False
Application.CutCopyMode = False
dataWB.Close False
Sheets(strListSheet).Select
ActiveCell.Offset(1, 0).Select
Loop
Sheets(strListSheet).Select
Range("B2").Select
Exit Sub
ErrH:
MsgBox "It seems some file was missing. The data copy operation is not complete."
Exit Sub
'Application.ScreenUpdating = True
End Sub
you can copy wb1 and past it as wb2
Sub Copy_One_File()
Dim wb1, wb2 As String
wb1 = ActiveWorkbook.Path & "wb1.xlsm"
wb2 = ActiveWorkbook.Path & "wb2.xlsm"
FileCopy wb1, wb2
End Sub
this is the simplest method
you should avoid Select/Selection/Activate/ActiveXXXpattern in favour of a fully qualified range reference
like in the following (commented) code:
Option Explicit
Sub GetData()
Dim strWhereToCopy As String, strStartCellColName As String
Dim strFileName As String
Dim strCopyRange As Range, cell As Range
Dim LastRow As Long
With Sheets("List") '<--| reference your "List" worksheet
For Each cell In .Range("B2", .Cells(.Rows.count, "B").End(xlUp)).SpecialCells(xlCellTypeConstants) '<--| loop through its column "B" not empty cells form row 2 down to last not empty one
With cell '<--| reference current cell
strFileName = .Offset(0, 1) & .Value
strCopyRange = .Offset(0, 2) & ":" & .Offset(0, 3)
strWhereToCopy = .Offset(0, 4).Value
strStartCellColName = Mid(.Offset(0, 5), 2, 1)
End With
On Error GoTo ErrH '<--| activate error handler for subsequent file open statement
Workbooks.Open strFileName, UpdateLinks:=False, ReadOnly:=True
On Error GoTo 0 '<--| resume "default" error handling
Range(strCopyRange).Copy '<-- without a leading dot (.) the range referes to the currently active worksheet, which is the active one in the just opened workbook
With .Parent '<--| reference workbook where currently referenced Sheet "List" resides in
LastRow = LastRowInOneColumn(.Worksheets(strWhereToCopy), strStartCellColName) '<--| your 'LastRowInOneColumn' function must be passed a worksheet reference, too
With .Worksheets(strWhereToCopy).Cells(LastRow + 1, 1) '<--| reference 'strWhereToCopy' named worksheet in the referenced workbook
.PasteSpecial xlPasteValues, xlPasteSpecialOperationNone
.PasteSpecial Paste:=xlPasteFormats, Operation:=xlNone, SkipBlanks:=False, Transpose:=False
Application.CutCopyMode = False
End With
End With
ActiveWorkbook.Close False
Next cell
.Activate
.Range("B2").Select
End With
Exit Sub
ErrH:
MsgBox "It seems some file was missing. The data copy operation is not complete."
End Sub
as per comments, your LastRowInOneColumn function must be passed a worksheet object reference too and fully qualify the column range reference to search the last row in
the function signature and its pseudocode is:
Function LastRowInOneColumn(sht As Worksheet, strStartCellColName As String) As Long
With sht
'here goes your actual 'LastRowInOneColumn' code
' only you have to put a dot (.) before each range reference
End With
End Function

Copying formula and Format from row above Macro

I have a spreadsheet for entering a new set of data on a new row each day each day, the row contains formulas and formatting. I want to be able to click a button and it adds a row under the last row with entered data and copy the formulas and formatting only, ready for new data to be entered.
Below is my code:
Sub Button1_Click()
Dim ws As Worksheet
Dim varUserInput As Variant
Set ws = ThisWorkbook.Sheets("Summary")
With ws
varUserInput = .Range("D" & .Rows.Count).End(xlUp).Row
.Rows(varUserInput).Insert Shift:=xlDown
.Rows(1).Copy .Rows(varUserInput)
.Rows(varUserInput - 1).Copy
.Rows(varUserInput + 1).PasteSpecial Paste:=xlPasteFormats, Operation:=xlNone, _
SkipBlanks:=False, Transpose:=False
End With
Application.CutCopyMode = False
End Sub
The issue is that it will only copy the formula from the same hidden row each time.
Is this what you are trying (UNTESTED)?
Sub Button1_Click()
Dim ws As Worksheet
Dim varUserInput As Variant
varUserInput = InputBox("Enter Row Number where you want to add a row:", "What Row?")
If varUserInput = "" Then Exit Sub
Set ws = ThisWorkbook.Sheets("Sheet1") '<~~ Change as applicable
With ws
.Rows(varUserInput).Insert Shift:=xlDown
.Rows(1).Copy .Rows(varUserInput)
.Rows(varUserInput - 1).Copy
.Rows(varUserInput).PasteSpecial Paste:=xlPasteFormats, Operation:=xlNone, _
SkipBlanks:=False, Transpose:=False
End With
Application.CutCopyMode = False
End Sub

Simples repeat macro in Excel

I've googled this but couldn't find a clear answer.
I have a workbook that contains lots of sheets, each sheet contains purchase order info.
I want to copy the same cell range from each sheet and compile a long list of all of those ranges.
my codes is currently;
Sub WorksheetLoop()
Sheets("5040001253").Select
Range("A4:O23").Select
Selection.Copy
Sheets("PO_Combi").Select
lastRow = ActiveSheet.Cells(Rows.Count, "A").End(xlUp).Row
ActiveSheet.Range("A" & lastRow + 1).Select
Selection.PasteSpecial Paste:=xlPasteValues, Operation:=xlNone, SkipBlanks _
:=False, Transpose:=False
Application.CutCopyMode = False
End Sub
My question is: is there a simple command that allows to replace the sheet named 5040001253 with that will make this macro repeat on all sheets? If not, could someone tell me what to do to make it so?
Next code copies Range("A4:O23") from each sheet (except PO_Combi) to column A of sheet PO_Combi:
Sub WorksheetLoop()
Dim sh As Worksheet
Dim shCombi As Worksheet
Dim lastrow As Long
Set shCombi = ThisWorkbook.Worksheets("PO_Combi")
For Each sh In ThisWorkbook.Worksheets
With shCombi
If sh.Name <> .Name Then
lastrow = .Cells(.Rows.Count, "A").End(xlUp).Row
sh.Range("A4:O23").Copy
.Range("A" & lastrow + 1).PasteSpecial xlPasteValues
End If
End With
Next
Application.CutCopyMode = False
End Sub