I am trying to find a specific value in a column in an Excel sheet, and then add a value (=1) three columns to the right.
My code:
Sub AddNote()
ActiveSheet.Range("F:F").Find(What:="Cat").Select
Selection.Offset(0, 4).Value = 1
End Sub
Only I got:
Error message 91: `Object variable or With block variable not set.
What is wrong with my commands?
Take a look at this :
Sub test_IngaB()
Dim FirstAddress As String, cF As Range, LookForString As String
LookForString = "Cat"
With ThisWorkBook.Sheets("Sheet's name").Range("F:F")
.Cells(1,1).Activate
'First, define properly the Find method
Set cF = .Find(What:=LookForString, _
After:=ActiveCell, _
LookIn:=xlFormulas, _
LookAt:=xlPart, _
SearchOrder:=xlByColumns, _
SearchDirection:=xlNext, _
MatchCase:=False, _
SearchFormat:=False)
'If there is a result, keep looking with FindNext method
If Not cF Is Nothing Then
FirstAddress = cF.Address
Do
cF.Offset(0, 3).Value = 1
Set cF = .FindNext(cF)
'Look until you find again the first result
Loop While Not cF Is Nothing And cF.Address <> FirstAddress
End If
End With
End Sub
Error message 91: `Object variable or With block variable not set.
this error means that searching is failed, there is no "Cat" in column
try this:
Sub test()
Dim rng As Range
Set rng = ActiveSheet.[F:F].Find("Cat")
If Not rng Is Nothing Then
rng.Offset(, 4).Value = 1
Else
MsgBox "Searching criteria does not exists in column [F]!"
End If
End Sub
and also one comment, avoid usage of the select and selection method, this is bad practice
If the .Find method doesn't output a range (there is no match for "Cat") then the .Offset method will halt into an error.
A structured solution would be along the lines of:
Sub AddNote()
Dim rng As Range
Set rng = ActiveSheet.Range("F:F")
If Application.WorksheetFunction.CountIfs(rng, "*Cat*") <> 0 Then 'if there is a match for "Cat" (LookAt:=xlPart), if you want exact matches, remove the asterisks
rng.Find(What:="Cat").Select
Selection.Offset(0, 4).Value = 1
End If
End Sub
Related
I would like to select the first non-blank row above the selected cell (minus offset). For example, if a find Machine 1 in the sheet Grupos Produção I want to return the ******* Grupo 1 ******* string.
********** Grupo 1 **********
Machine 1
Machine 2
I have the following so far, but it's not returning what I need.
Dim FindString As String
Dim Rng As Range
FindString = Lcell.Value
If Trim(FindString) <> "" Then
With Sheets("Grupos Produção").Range("A:Z")
Set Rng = .Find(What:=FindString, _
After:=.Cells(.Cells.Count), _
LookIn:=xlValues, _
LookAt:=xlWhole, _
SearchOrder:=xlByRows, _
SearchDirection:=xlNext, _
MatchCase:=False)
If Not Rng Is Nothing Then
Application.Goto Rng, True
upperRow = .Cells(Rng.Row, Rng.Column - 1).End(xlDown).Row
Else
MsgBox "Nothing found"
End If
End With
End If
I'm not sure I understand your code, but I think you are looking for something like this:
...
...
If Not Rng Is Nothing Then
Do While Rng.Row > 1 And Rng.Offset(-1, 0).Value <> ""
Set Rng = Rng.Offset(-1, 0)
Loop
...
Once the cell is found, it works its way up until it finds an empty cell and stops just before.
This will find the first non-blank cell (which will indicate the row is not blank) above the selected cell.
You need to check for:
If the rest of the sheet is empty it will return the same address as your selection.
If all cells above the selection are empty it will start from the bottom of the sheet until it reaches your selection again.
As you said the first non-blank cell it's using the * wildcard to search, and to make it look up from the selection it uses xlPrevious.
Still need to check if rng is nothing in case the entire sheet is empty.
Sub Test()
Dim Rng As Range
With ThisWorkbook.Worksheets("Sheet1").Range("A:Z")
Set Rng = .Cells.Find(What:="*", _
After:=Selection, _
LookIn:=xlValues, _
LookAt:=xlWhole, _
SearchOrder:=xlByRows, _
SearchDirection:=xlPrevious)
If Not Rng Is Nothing Then
If Rng.Address = Selection.Address Or Rng.Row > Selection.Row Then
MsgBox "Nothing found"
Else
Rng.Select
End If
End If
End With
End Sub
I managed to get what I need based on #Sam 's answer
If Not Rng Is Nothing Then
Do While Rng.Row > 1 And Rng.Offset(-1, 0).Value <> ""
Set Rng = Rng.Offset(-1, 0)
Loop
grupo = Rng.Offset(-1, -1).Value
Lcell.Value = grupo
End If
So I have a part in my macro that I want to add what I assume needs to be an "Else" portion, but I am not that good with macros and am asking for help.
Range("Z1").Copy
Dim FindString As String
Dim Rng As Range
FindString = Sheets("Pull").Range("Y1").Value
If Trim(FindString) <> "" Then
With Sheets("HourTracker").Range("A:A")
Set Rng = .Find(What:=FindString, _
After:=.Cells(.Cells.Count), _
LookIn:=xlValues, _
LookAt:=xlWhole, _
SearchOrder:=xlByRows, _
SearchDirection:=xlNext, _
MatchCase:=False)
If Not Rng Is Nothing Then
Application.Goto Rng, True
Else
MsgBox "Nothing found"
End If
End With
ActiveCell.Offset(0, 1).Activate
Selection.PasteSpecial xlPasteValues
Application.DisplayAlerts = True
End If
End Sub
So what I want this to do, is instead of "MsgBox "Nothing Found"", I want it to essentially perform the same thing as above, but copy cell Z2, and search for the value of Y2 in the same sheet "HourTracker" then paste the value. I have no idea on how to accomplish this, and all my attempts have failed. Any help would be much appreciated. Let me know if you need more clarification, thank you in advance!!!
Sounds to me like you're looking for a loop.
Sub findStuff()
Application.DisplayAlerts = False
' The item you want to paste
Dim PasteString As String
' The item you're looking for
Dim FindString As String
' The range that may containing FindString
Dim Rng As Range
' The variable used to loop through your range
Dim iCounter as Long
' loop through the first cell in column Y to the last used cell
For iCounter = 1 To Sheets("Pull").Cells(Rows.Count, 25).End(xlUp).Row
' PasteString = the current cell in column Z
PasteString = Sheets("Pull").Cells(iCounter, 26).Value
' FindString = the current cell in column Y
FindString = Sheets("Pull").Cells(iCounter, 25).Value
If Trim(FindString) <> "" Then
With Sheets("HourTracker").Range("A:A")
' Find the cell containing FindString
Set Rng = .Find(What:=FindString, _
After:=.Cells(.Cells.Count), _
LookIn:=xlValues, _
LookAt:=xlWhole, _
SearchOrder:=xlByRows, _
SearchDirection:=xlNext, _
MatchCase:=False)
If Not Rng Is Nothing Then
' There's no need to activate/ select the cell.
' You can directly set the value with .Value
Rng.Offset(0, 1).Value = PasteString
Else
' Do nothing
End If
End With
Else
' Do nothing
End If
Next
Application.DisplayAlerts = True
End Sub
Every time the compiler hits Next it will start again at For but raise the value of iCounter by 1. We can use Cells to accomplish this since Cells takes the row and column arguments as numbers, not strings (like Range). The syntax is simply Cells(Row #, Column #). Therefore, every time the For . . . Next loops around again, iCounter will go up by one and you'll search in the next row.
Instead of using .Paste, you can set the value of a cell directly with .Value. Pasting is pretty slow and using .Value is much faster.
Cells().End(xlUp).Row is a method used to find the last used cell in a range. See Error in finding last used cell in VBA for a much better explanation than I can give here.
I have the following nodes:
Expected output:
My current steps to get this are:
Delimit by "/"
Sort
Conditionally format some cells. I'm trying to make the cells blank by doing A2=A1 and setting the font color to white. However this is not working.
How can I do that using VBA? I am told that this would probably require VBA.
The trick is keeping only one of the parent nodes per line.
Try with formulas (in new sheet or column) like
X2 =IF(A2=A1,"",A2)
X3 =IF(A3=A2,"",A3)
X4 =IF(A4=A3,"",A4)
etc..
For column A
Quick and dirty, but it gets the job done. This will loop through columns A-F rows 1-12 and select the value for each cell find that occurrence and delete the second occurrence not the first. This should do the trick.
Sub findItemInColumns()
With ThisWorkbook.Worksheets("Sheet1")
For r = 1 To 12
For c = 1 To 6
RemoveDups .Cells(r, c).Value
Next
Next
End With
End Sub
Sub RemoveDups(ByVal somevalueToFindAndRemove As String)
Dim FindString As String
Dim Rng As Range
listOfValues = Array(somevalueToFindAndRemove)
If Trim(somevalueToFindAndRemove) <> "" Then
With Sheets("Sheet1").Range("A:AK")
For i = LBound(listOfValues) To UBound(listOfValues)
Set Rng = .Find(What:=listOfValues(i), _
After:=.Cells(.Cells.Count), _
LookIn:=xlValues, _
LookAt:=xlWhole, _
SearchOrder:=xlByRows, _
SearchDirection:=xlNext, _
MatchCase:=False)
If Not Rng Is Nothing Then
FirstAddress = Rng.Address
Do
Application.Goto Rng, True
If Rng.Address <> FirstAddress Then Rng.Value = ""
Set Rng = .FindNext(Rng)
Loop While Not Rng Is Nothing And Rng.Address <> FirstAddress
End If
Next i
End With
End If
End Sub
Here's my code:
Option Explicit
Private Sub CBu_Login_Click()
Dim ws As Worksheet, rng As Range, lrow As Long, find_value As String
Dim cel As Range
Set ws = ThisWorkbook.Sheets("UserName")
lrow = ws.Range("A" & ws.Rows.Count).End(xlUp).Row
Set rng = ws.Range("A2:A" & lrow)
find_value = Me.TB_Username.Value
Set cel = rng.Find(What:=find_value, After:=ActiveCell, LookIn:=xlFormulas, _
LookAt:=xlPart, SearchOrder:=xlByRows, SearchDirection:=xlNext, _
MatchCase:=False, SearchFormat:=False)
If Not cel Is Nothing Then
If Me.TB_Password.Value = cel.Offset(0, 1).Value Then
UF_Encoding.L_User.Caption = "Welcome " & cel.Offset(0, 2).Value & "!" & " You are logged in."
UF_Encoding.TB_Operator.Text = cel.Offset(0, 2).Value
UF_Encoding.Show
Me.Hide
Else
MsgBox "Invalid Username/Password"
End If
Else
MsgBox "Invalid Username/Password"
End If
End Sub
This code is giving me a Type Mismatched error on the .Find part.
The code is in a Command Button.
Also, this works sometimes and then suddenly will throw up the Mismatched Error.
Please help why it is throwing the error and how to correct it.
I don't want to resort to looping since i have many users.
Avoid the use of ActiveCell, unless there's an absolutely necessary reason to incorporate it.
Please see THIS LINK
Simply change
After:=ActiveCell
to
After:=ws.Range("A2")
One possible solution. I've commented everything, so that you can follow the specific steps.
Sub Hide_Me()
Dim rngHeadings As Range 'the range where your headings are
Dim arrHideColumns() As Variant 'the array, where you list all headings that should be hidden
Dim Item As Variant 'a common variable for the for-each-loop
Dim rngResult As Range 'the range for the search result
'Assign the range, where your headings are
Set rngHeadings = Worksheet1.Range("C3:E3")
'List the headings you want to be hidden
arrHideColumns = Array("Address", "Phone Number")
'Loop through your list
For Each Item In arrHideColumns
'Use the .FIND method of the range-object
'Please read more about this method here: https://learn.microsoft.com/en-us/office/vba/api/excel.range.find
Set rngResult = rngHeadings.Find(Item)
'If there is a result
If Not rngResult Is Nothing Then
'Hide the column
rngResult.EntireColumn.Hidden = False
End If
Next
End Sub
Every call of this Function results in a Runtime Error '13' Type Mismatch. Why does this happen?
Public Function VersionExists(versionId As String)
VersionExists = False
For Each cell In Tabelle2.Columns(1)
If cell.Value = versionId Then
VersionExists = True
End If
Next
End Function
You can't access cell.value from .Columns(1) as it returns a range encompassing the entire column, instead;
For Each cell In Sheet1.Columns(1).Rows '//or .cells
Probably a good idea to exit the for loop after a match too.
Here is an alternative as I suggested in the comment
Public Function VersionExists(versionId As String) As Boolean
Dim aCell As Range, rng As Range
Set rng = Tabelle2.Columns(1)
Set aCell = rng.Find(What:=versionId, LookIn:=xlValues, _
LookAt:=xlWhole, SearchOrder:=xlByRows, SearchDirection:=xlNext, _
MatchCase:=False, SearchFormat:=False)
If Not aCell Is Nothing Then VersionExists = True
End Function