vba to copy to different ranges - vba

I have this sheet called Consulta where everytime I change the value on the column K it changes the color of the range E:K to green or white if it's empty.
I also want to if the row is green, copy that row to the sheet called E-mail. This is what I've tried so far and it works:
Sub ChangeColor()
Dim ws As Worksheet, ws1 As Worksheet, i As Long, lastrow As Long
Set ws = Sheets("Consulta")
Set ws1 = Sheets("E-mail")
lastrow = ws.Cells(Rows.Count, "E").End(xlUp).Row
For i = 5 To lastrow
If ws.Range("K" & i) <> "" Then
ws.Range("E" & i & ":K" & i).Interior.ColorIndex = 43
ws.Range("E" & i & ":K" & i).Copy ws1.Range("A" & i & ":G" & i)
Else
ws.Range("E" & i & ":K" & i).Interior.ColorIndex = 2
End If
Next
If ws.Range("E" & i & ":K" & i).Interior.ColorIndex = 2 Then
ws1.Range("A" & i & ":G" & i).Clear
End If
End Sub
My problem is with this line below:
ws.Range("E" & i & ":K" & i).Copy ws1.Range("A" & i & ":G" & i)
I actually want to copy to a different range instead of the corresponding range in the sheet E-mail (for example, if the first match is E3:K3 I want to copy to A2:K2. If the second match is E34:K34 I want to copy it to A3:K3 and so it goes).
I tried using another loop but my Excel got crazy so I think I did it wrong.
Any suggestions will be appreciated.

You only need the upper-left corner cell for a destination. Look from the bottom up for the last used cell and offset down a row.
with ws1
ws.Range("E" & i & ":K" & i).Copy .cells(.rows.count, "A").end(xlup).offset(1, 0)
end with
You might want to put this above the line that applies a fill color or you will be copying the fill color as well.

Related

Insert formula with Variable VBA

I'm trying to insert a formula in the Column C of Sheet2. The row number however depends on the value of pasterow. The range in the formula should be G[lastrow]:NS[lastrow] with lastrow pertaining to the last row of Sheet1.
Here is my code:
Sub try()
With Sheets("Sheet2")
pasterow = .Cells(.rows.Count, "B").End(xlUp).Offset(1, 0).Row
With Sheets("Sheet1")
lastRow = ActiveWorkbook.Worksheets("Sheet1").Range("F" & .rows.Count).End(xlUp).Row
ActiveWorkbook.Worksheets("Sheet2").Range("C" & pasterow).formula = _
"=COUNTIF(Sheet1!G & lastRow & :NS & lastRow & , ""VL"" )"
End With
End With
End Sub
I'll really appreciate if someone could point out what's wrong with my code. Thanks!
The VBA variables are inside your formula string. Compare:
ActiveWorkbook.Worksheets("Sheet2").Range("C" & pasterow).formula = "=COUNTIF(Sheet1!G" & lastrow & ":NS" & lastrow & ", ""VL"" )"
Try this..
ActiveWorkbook.Worksheets("Sheet2").Range("C" & pasterow).FormulaR1C1 = "=COUNTIF(Sheet1!C[4]:C[380],""VL"")"
May be this is what your expecting to achieve!
ActiveWorkbook.Worksheets("Sheet2").Range("C" & pasterow).Value = "=COUNTIF(Sheet1!G" & lastRow & ":NS" & lastRow & ", ""VL"" )"
Try with:
ActiveWorkbook.Worksheets("Sheet2").Range("C" & pasterow).formula = _
"=COUNTIF(Sheet1!R" & lastrow & "C7:R" & lastrow & "C383,""VL"")"

VBA Copy column data to last row of different column, do for multiple columns, loop through all worksheets do same

Trying to copy data from Column F (F2:F) then paste into first empty row of Column D.
Then do same for Column G (G2:G), paste to first empty row of E.
Data from H paste to (new first empty row of D).
Data from I paste to (new first empty row of E).... Through Column M
Needs to Loop through all Worksheets in Workbook and do the exact same thing.
Problem: "Syntax Error" on all the lines:
ActiveSheet.Range(“F2:F” & copyLastrow).Copy Destination:=ActiveSheet.Range(“D” & pasteLastrowD)
They are all hilighted in red
I think that my problem is that I don't know how the naming convention for Active.Sheet
Code so far:
Sub Doit()
Dim ws As Worksheet
For Each ws In Worksheets
copyLastrow = ActiveSheet.Cells.Find("*", searchorder:=xlByRows, searchdirection:=xlPrevious).Row
pasteLastrowD = ActiveSheet.Range(“D” & Rows.Count).End(xlUp).Row + 1
ActiveSheet.Range(“F2:F” & copyLastrow).Copy Destination:=ActiveSheet.Range(“D” & pasteLastrowD)
pasteLastrowE = ActiveSheet.Range(“E” & Rows.Count).End(xlUp).Row + 1
ActiveSheet.Range(“G2:G” & copyLastrow).Copy Destination:=ActiveSheet.Range(“E” & pasteLastrowE)
pasteLastrowD = ActiveSheet.Range(“D” & Rows.Count).End(xlUp).Row + 1
ActiveSheet.Range(“H2:H” & copyLastrow).Copy Destination:=ActiveSheet.Range(“D” & pasteLastrowD)
pasteLastrowE = ActiveSheet.Range(“E” & Rows.Count).End(xlUp).Row + 1
ActiveSheet.Range(“I2:I” & copyLastrow).Copy Destination:=ActiveSheet.Range(“E” & pasteLastrowE)
pasteLastrowD = ActiveSheet.Range(“D” & Rows.Count).End(xlUp).Row + 1
ActiveSheet.Range(“J2:J” & copyLastrow).Copy Destination:=ActiveSheet.Range(“D” & pasteLastrowD)
pasteLastrowE = ActiveSheet.Range(“E” & Rows.Count).End(xlUp).Row + 1
ActiveSheet.Range(“K2:K” & copyLastrow).Copy Destination:=ActiveSheet.Range(“E” & pasteLastrowE)
pasteLastrowD = ActiveSheet.Range(“D” & Rows.Count).End(xlUp).Row + 1
ActiveSheet.Range(“L2:L” & copyLastrow).Copy Destination:=ActiveSheet.Range(“D” & pasteLastrowD)
pasteLastrowE = ActiveSheet.Range(“E” & Rows.Count).End(xlUp).Row + 1
ActiveSheet.Range(“M2:M” & copyLastrow).Copy Destination:=ActiveSheet.Range(“E” & pasteLastrowE)
Next
End Sub
Re my comment above, have just amended the first couple but hopefully you get the idea. You need to fully reference all range/cell references. You do also need to change the quotes though.
Sub Doit()
Dim ws As Worksheet
For Each ws In Worksheets
copyLastrow = ws.Cells.Find("*", searchorder:=xlByRows, searchdirection:=xlPrevious).Row
pasteLastrowD = ws.Range("D" & Rows.Count).End(xlUp).Row + 1
ws.Range("F2:F" & copyLastrow).Copy Destination:=ws.Range("D" & pasteLastrowD)
'etc
Sub Doit()
Dim ws As Worksheet
For Each ws In Worksheets
With ws
For Each cell In .Range("F2:M2")
.Range(cell, .Cells(.Rows.Count, cell.Column).End(xlUp).Copy Destination:=.Cells(.Rows.Count, "D").End(xlUp).Offset(1, cell.Column Mod 2)
Next cell
End With
Next ws
End Sub

Using a formula in a range of cells

I want to use a formula in a range of cells but I get the formula in that cell and not the results of the formula.
I tried a couple of different ways.
The first script I tried entered the formula all the way down the column until the last row value: -
Dim LastRow As Long
LastRow = Cells(Rows.Count, 5).End(xlUp).Row
Range("DO22:DO" & LastRow).Formula = "IF=COUNTIF(AS22:AU" & LastRow & " ,""=Major Variance"")>0,""Major Variance"",IF(COUNTIF(AS22:AU" & LastRow & " ,""=Minor Variance"")>0,""Minor Variance"",""On Track""))"
This is the other script I tried but this puts the formula only in the first row of the range: -
Dim LastRow As Long
Dim Rng As Range
Range("DO22:DO" & LastRow).Select
For Each Rng In Range("DO22:DO" & LastRow)
ActiveCell.Formula = "IF=COUNTIF(AS22:AU" & LastRow & " ,""=Major Variance"")>0,""Major Variance"",IF(COUNTIF(AS22:AU" & LastRow & " ,""=Minor Variance"")>0,""Minor Variance"",""On Track""))"
Next Rng
Edit 1
I have made a change to the code as per someone's answer but I am now getting an run-time error 'Application-defined or object defined error.
It only seems to happen when I add the extra = in front of the If. The error appears on the line
Rng.Formula = "=IF=COUNTIF(AS22:AU" & LastRow & " ,""=Major Variance"")>0,""Major Variance"",IF(COUNTIF(AS22:AU" & LastRow & " ,""=Minor Variance"")>0,""Minor Variance"",""On Track""))"
Here is the edited script: -
Dim Rng As Range
Dim LastRow As Long
LastRow = Cells(Rows.Count, 5).End(xlUp).Row
Range("DO22:DO" & LastRow).Select
For Each Rng In Range("DO22:DO" & LastRow).Cells
Rng.Formula = "=IF=COUNTIF(AS22:AU" & LastRow & " ,""=Major Variance"")>0,""Major Variance"",IF(COUNTIF(AS22:AU" & LastRow & " ,""=Minor Variance"")>0,""Minor Variance"",""On Track""))"
Rng.Value = Rng.Value
Next Rng
You have a malformed IF function and COUNTIF function.
'target formula "=IF(COUNTIF(AS22:AU99, "Major Variance"), "Major Variance", =IF(COUNTIF(AS22:AU99, "Minor Variance"), "Minor Variance", "On Track"))
rng.Formula = "=IF(COUNTIF(AS22:AU" & lastRow & ", ""Major Variance""), ""Major Variance"", " & _
"IF(COUNTIF(AS22:AU" & lastRow & ", ""Minor Variance""), ""Minor Variance"", " & _
"""On Track""))"
rng = rng.Value
Note that if both Major Variance and Minor Variance exist, then Major Variance takes precedence.
To put this formula into each row and modify the row each time in a loop, the code would look like this.
Dim lastRow As Long, rng As Range
With Worksheets("Sheet1") '<~~ you should know what worksheet you are on!
lastRow = .Cells(Rows.Count, 5).End(xlUp).Row
For Each rng In .Range("DO22:DO" & lastRow)
rng.Formula = "=IF(COUNTIF(AS" & rng.Row & ":AU" & rng.Row & ", ""Major Variance""), ""Major Variance"", " & _
"IF(COUNTIF(AS" & rng.Row & ":AU" & rng.Row & ", ""Minor Variance""), ""Minor Variance"", " & _
"""On Track""))"
rng.Value = rng.Value
Next rng
End With
But you can also put the formula into all of the cells at once like this.
Dim lastRow As Long
With Worksheets("Sheet1") '<~~ you should know what worksheet you are on!
lastRow = .Cells(Rows.Count, 5).End(xlUp).Row
With .Range("DO22:DO" & lastRow)
.Formula = "=IF(COUNTIF(AS22:AU22, ""Major Variance""), ""Major Variance"", " & _
"IF(COUNTIF(AS22:AU22, ""Minor Variance""), ""Minor Variance"", " & _
"""On Track""))"
.Value = .Value
End With
End With
You are using activecell in the 2nd one so it will only be in the active cell if not selected. so you need to change your loop to be
For Each Rng In Range("DO22:DO" & LastRow).cells
and then
rng.Formula = "=IF=COUNTIF(AS22:AU" & LastRow & " ,""=Major Variance"")....
then
rng.value=rng.value
also, in the 2nd one, youre not setting LastRow.

copy value not formula of column vba

I have a problem with values i try to copy...
Let's say the value of A33 is 1655, formula for the cell is IFERROR('L-Logic'!G14;"") and when copied it displays 0 and if i cklick on that copied cell it displays the formula. why is that? Should i have to paste special values? Any suggestions?
Am I on the right path? And if I wan't to check cells values, I was thinking to use this..
If ws.Cells(i, 1) <> "blabla" Then ws.Range("A1:A50" & lastrow).Copy Destination:=Work
Below is my sample code. Regards
For Each Ws In Sheets(Array("List 1", "list 2", "List3"))
lastrow = Ws.Range("A" & Rows.Count).End(xlUp).row
For i = 1 To lastRow
If ws.cells(i, 1)<> "testtest" Then
Ws.Range("C1:C50" & lastrow).Copy Destination:=Worksheets("Master list").Range("D" & lastRowMaster)
Ws.Range("A1:A50" & lastrow).Copy Destination:=Worksheets("Master list").Range("A" & lastRowMaster)
Ws.Range("L1:L50" & lastrow).Copy Destination:=Worksheets("Master list").Range("B" & lastRowMaster)
Ws.Range("L1:L50" & lastrow).Copy Destination:=Worksheets("Master list").Range("C" & lastRowMaster)
lastRowMaster = lastRowMaster + Range("C1:C" & lastrow).Rows.Count
Next i
Next
I like what you did with lastRowMaster.
For direct value transfer, you would reverse them.
lrm = 1
With Worksheets("MasterList")
For Each ws In Sheets(Array("List1", "List2", "List3"))
lr = ws.Range("A" & Rows.Count).End(xlUp).Row
.Range("D" & lrm).Resize(lr, 1) = ws.Range("C1:C" & lr).Value2
.Range("A" & lrm).Resize(lr, 1) = ws.Range("A1:A" & lr).Value2
.Range("B" & lrm).Resize(lr, 1) = ws.Range("L1:L" & lr).Value2
.Range("C" & lrm).Resize(lr, 1) = ws.Range("L1:L" & lr).Value2
lrm = lrm + Range("A1:A" & lr).Rows.Count
Next
'...
End With
The destination needs to be resized to accommodate the value transfer. It is not sufficient to just reference the top cell like copy and paste. Be careful with the ones that start at row 7. You will have to do a little maths to get the Range.Resize property correct.

Use the last row count in a formula

The following code allows me to repeat a formula from row 2 to all rows up to the last active row.
Dim LastRow As Long
With Sheets("C PUR TYPE")
LastRow = .Cells(.Rows.Count, "A").End(xlUp).Row
.Range("M2:M" & LastRow).formula = "=IFERROR(RIGHT(SUBSTITUTE(Lookup_concat(A2,$A$2:$A1932,$L$2:$L1932),"" 0,"",""""),LEN(SUBSTITUTE(Lookup_concat(A2,$A$2:$A1932,$L$2:$L1932),"" 0,"",""""))-2),"" - "")"
End With
In this instance there are 1'932 active rows.
Is there a way that I can replace the cell reference :$A1932 and $L1932 in the formula to using the last row count as the row count will be different each time the report runs.
Thanks
Using & will allow you to concatenate the variable into the string:
Dim LastRow As Long
With Sheets("C PUR TYPE")
LastRow = .Cells(.Rows.Count, "A").End(xlUp).Row
.Range("M2:M" & LastRow).formula = "=IFERROR(RIGHT(SUBSTITUTE(Lookup_concat(A2,$A$2:$A" & LastRow & ",$L$2:$L" & LastRow & "),"" 0,"",""""),LEN(SUBSTITUTE(Lookup_concat(A2,$A$2:$A" & LastRow & ",$L$2:$L" & LastRow & "),"" 0,"",""""))-2),"" - "")"
End With
Seems to me like you can use a variable similar to how you calculated lastRow.
Example (assuming you don't have any blanks in column A):
dim LookupLastrow as long
LookupLastrow=range("A1").end(xldown).row
then replace the 1932 references in your formula with " & lookuplastrow & ":
.Range("M2:M" & LastRow).formula = "=IFERROR(RIGHT(SUBSTITUTE(Lookup_concat(A2,$A$2:$A" & lookuplastrow & ",$L$2:$L" & lookuplastrow & "),"" 0,"",""""),LEN(SUBSTITUTE(Lookup_concat(A2,$A$2:$A" & lookuplastrow & ",$L$2:$L" & lookuplastrow & "),"" 0,"",""""))-2),"" - "")"