Select Row in Excel with VBA if complete - excel

I want to select each row that is complete. So each row where there is no empty cell.
The selected row should then be exported to a sharepoint list.
so far the code I tried works but exports the whole table. I want to add a line that selects and exports only the rows that have no blank cells.
I had something like the following in mind. But I don't know how to select the complete rows from the entire table instead of specifying the cells.
If Cells().Value not isnull then
Range().EntireColumn.Select
Sub ExportToSharePoint ()
ActiveSheet.ListObjects("Table1").Publish Array("https://sharepoint...", "Name of the List")_, True
ActiveCell.Select
End Sub

You can loop through your table and get the completed rows using the following
Option Explicit
Public Sub ExportToSharePoint()
Dim r
With ActiveSheet.ListObjects("Table1")
For Each r In .DataBodyRange.Rows
If WorksheetFunction.CountA(.Parent.Range(r.Address)) = .ListColumns.Count Then
' Rest of your code here
End If
Next r
End With
End Sub

Related

Adding msgbox if my pivot table has empty cells

enter image description hereI have an Excel workbook that runs a macro and in the end displays everything in a pivot table
I am trying to add a msgbox when my pivot table has an empty cell (at the end of my macro)
I already did the conditional formatting version(color blank cells red) and it works fine, but the client wants a msgbox to alert him.
I found a IsEmpty command that should work but I cant seem to make it look only inside said pivot table.
Here is what I tried:
Sub IsEmpty()
If IsEmpty(ActiveSheet.Range("PivotTables(1)")) = True Then
'Cell A2 is not blank
MsgBox "Cell A2 is empty"
Else
End If
End Sub
I'm sure the way my If statement is written is false. Just cant seem to find the right syntax.
Thanks in advance
Picture added; I want the macro to target pivot's C column. However, you cant know which cell will be empty or how long the list will continue.
And if just make Excel check a broad spectrum(c2:c300), there will always be en empty cell after the pivot table is finished.
There might be a loop you can create but its way over my current skill set.
The pivot table's name is "PivotTable2"
Is there a to search only in the pivot table's column c for empty cells?
Please consider the capabilities of the function below. It will return True or False depending upon the count of items in columns A and C. In column A text, number or function is counted. In column C there must be a number in each cell. If both counts are the same the function returns True. Either count can be further refined if there are exceptions which the current function doesn't correction evaluate.
Function IsComplete() As Boolean
' 025
Dim Rng As Range
With ThisWorkbook.Sheets("PivotTables(1)") ' change to suit
' set a range from A3 to end of column A
Set Rng = .Range(.Cells(3, "A"), .Cells(.Rows.Count, "A").End(xlUp))
End With
With Application.WorksheetFunction
IsComplete = (.CountA(Rng) = .Count(Rng.Offset(0, 2)))
End With
End Function
You can use code to call this function and display a message box for True and another one if the function returns False. The code can be hitched to a button on your sheet, anywhere in your workbook.
Sub CommandButton1_Click()
Dim Txt As String
If IsComplete Then
Txt = "The pivot table was created without mistakes."
Else
Txt = "Some data are missing in the pivot table."
End If
MsgBox Txt, vbInformation, "Action report"
End Sub
You can also call the function as a UDF and display True or False in a cell of any sheet in your workbook. The UDF call would be like =IsComplete(). You might also embed the UDF call in an IF condition and display another text on your worksheet.
=IF(IsComplete(),"All's well","Missing Item")
In fact, you could slightly modify the function to return the difference between one count and the other and display "1 item missing". The possibilities are endless because the function is so versatile.

Selected row in listbox copied to another listbox

I have a listbox within a userform with a few rows of filtered data. I would like to be able to select one of the rows and have it appear in another listbox (just the values within that selected row, none of the others)
My current code is just:
Private Sub SelectHousingList_Click()
HousingList.Text = SelectHousingList.Selected(Row)
End Sub
With 'HousingList' being the listbox that I'd like the values to move to.
And 'SelectHousingList' being the rows of filtered data.
Previously in this code I've used code similar to this to select from a list of values (but not with a whole row of values).
Private Sub MaterialList_Click()
SelectedMaterialText.Value = MaterialList.Text
Worksheets("FSC PSC PFC").Range("D4").Value = SelectedMaterialText.Value
End Sub
The second line of code allows for the selected item in the list to be copied to a textbox.
If you need more of my code I can supply you with it.
This may be a simple question but I can't seem to find the answer anywhere or figure out code that allows it to happen.
Thank you in advance!
If I understand your requirements, this should do what you need for a single column:
Private Sub SelectHousingList_Click()
HousingList.AddItem SelectHousingList.Value
End Sub
If there are 2 columns, then this:
Private Sub SelectHousingList_Click()
HousingList.AddItem SelectHousingList.List(SelectHousingList.ListIndex)
HousingList.List(HousingList.ListCount - 1, 1) = SelectHousingList.List(SelectHousingList.ListIndex, 1)
End Sub
You'll need to add additional lines for every column beyond 2, changing the index for each one.
This code retrieves in an array (or string) all the columns values on the selected row. It fills the second listbox with as many columns first one has:
Private Sub SelectHousingList_Click()
Dim arrRow() As Variant, i As Long
ReDim arrRow(Me.SelectHousingList.ColumnCount)
For i = 0 To SelectHousingList.ColumnCount
arrRow(i) = Me.SelectHousingList.List(i, Me.SelectHousingList.ListIndex)
Next i
Debug.Print Join(arrRow, ", ")
With Me.HousingList
.ColumnCount = Me.SelectHousingList.ColumnCount
.AddItem arrRow(0)
For i = 1 To UBound(arrRow)
.List(.ListCount - 1, i) = arrRow(i)
Next i
End With
End Sub

How to autopopulate excel column based on dropdown list selection from another column

I have a spreadsheet that has two buttons - To retrieve rows from a sql table using a macro and another one to update data changes back to the table from excel. I have also attached an image here for reference. The table columns are EmpID, EName, Grouping, CCNum,CCName, ResTypeNum, ResName and Status.
Now to update changes, I have drop down lists for CCName and ResName. I would like the ResTypeNum to change automatically whenever the value in ResName column from dropdown list changes. Using Vlookup doesn't seem to work as the formula gets wiped out every time I click on the Retrieve button to refresh data. Also, I have to drag down the formula which I don't want but instead the value in ResTypeNum should automatically update whenever the ResName column is changed. I would appreciate any new ideas to make this work.
Thank you,
Hema
Assumptions:
First value is in A4
ResName column is G
Sheet with data validation list and corresponding code in sheet "ResNameSheet"
In the tables sheet event module you place the following code:
Private Sub Worksheet_Change(ByVal Target As Range)
If Target.Column = 7 And Target.Row > 3 Then
If Target.Value2 = "" Then
Target.Offset(0, -1).Value2 = ""
Exit Sub
End If
Dim rngDataValidation As Range
Dim rngRow As Range
Set rngDataValidation = ThisWorkbook.Sheets("ResNameSheet").UsedRange
For Each rngRow In rngDataValidation.Rows
If rngRow.Cells(1, 1).Value2 = Target.Value2 Then
Target.Offset(0, -1).Value2 = rngRow.Cells(1, 2).Value2
End If
Next
End If
End Sub
Explaining how the code works:
Fires on changes to the sheet
checks if changes are in column G (7) and that it occurs below the header row (3)
Checks that the change was not deleting from column G, if it is it clears all values on the corresponding column F
Loops through the Rows collection in the range with ResName list
Checks if values match
If it does it writes the corresponding code to the column to left of Target
Hope this helps.

Excel Insert Rows - Using Named Ranges To Hide Rows

I have hidden rows with checkbox macros
Every time I want to insert a new row, the vba code gets messed up and the code assigned to hide rows below will not work
is there a way to dynamically have the rows change the code in the vba
So I don't have to redo all the row values and check boxes that move in the process
[IMG]http://i39.tinypic.com/2akek5z.jpg[/IMG]
Sub CheckBox1_Click()
If Range("B3").Value = True Then
Rows("4:18").EntireRow.Hidden = False
Else
Rows("4:18").EntireRow.Hidden = True
End If
End Sub
Sub CheckBox2_Click()
If Range("B51").Value = True Then
Rows("52:66").EntireRow.Hidden = False
Else
Rows("52:66").EntireRow.Hidden = True
End If
End Sub
I have about 10 subcheckboxes in the code
If I insert or delete a row the code below will not work.
This is because the rows have changed
from the original code that I wrote
Edit
Use 'Named Ranges' instead of hard coding the range. The named range will automatically update when you insert a new row. For example:
I selected rows 9 thru 13 and named them 'RowsABC' as shown here:
I also named my checkbox cell as 'CheckABC' so that it is no longer dependent on what row it's in.
Your code now looks like this:
If Range("CheckABC").Value = True Then
Range("RowsABC").EntireRow.Hidden = False
Else
Range("RowsABC").EntireRow.Hidden = True
End If
Now you can select a row such as row 10 and right click -> insert, and your macro will hide rows 9:14 instead of 9:13 because the named range will update automatically when you insert.

How to select clear table contents without destroying the table?

I have a vba function in excel 2010 that I built using help from people on here. This function copies the contents of a table/form, sorts them, and sends them to the appropriate tables.
Now after running this function I want the original table to be cleared. I can achieve this with the following code, assuming ACell has been defined as the first cell in the table.
ACell.ListObject.Range.ClearContents works fine, the only problem is it deletes the table as well as the data values.
Is there any way around this? I would rather not have to set the table up every time I enter some data.
How about:
ACell.ListObject.DataBodyRange.Rows.Delete
That will keep your table structure and headings, but clear all the data and rows.
EDIT: I'm going to just modify a section of my answer from your previous post, as it does mostly what you want. This leaves just one row:
With loSource
.Range.AutoFilter
.DataBodyRange.Offset(1).Resize(.DataBodyRange.Rows.Count - 1, .DataBodyRange.Columns.Count).Rows.Delete
.DataBodyRange.Rows(1).Specialcells(xlCellTypeConstants).ClearContents
End With
If you want to leave all the rows intact with their formulas and whatnot, just do:
With loSource
.Range.AutoFilter
.DataBodyRange.Specialcells(xlCellTypeConstants).ClearContents
End With
Which is close to what #Readify suggested, except it won't clear formulas.
Try just clearing the data (not the entire table including headers):
ACell.ListObject.DataBodyRange.ClearContents
I reworked Doug Glancy's solution to avoid rows deletion, which can lead to #Ref issue in formulae.
Sub ListReset(lst As ListObject)
'clears a listObject while leaving row 1 empty, with formulae
With lst
If .ShowAutoFilter Then .AutoFilter.ShowAllData
On Error Resume Next
With .DataBodyRange
.Offset(1).Rows.Clear
.Rows(1).SpecialCells(xlCellTypeConstants).ClearContents
End With
On Error GoTo 0
.Resize .Range.Rows("1:2")
End With
End Sub
There is a condition that most of these solutions do not address. I revised Patrick Honorez's solution to handle it. I felt I had to share this because I was pulling my hair out when the original function was occasionally clearing more data that I expected.
The situation happens when the table only has one column and the .SpecialCells(xlCellTypeConstants).ClearContents attempts to clear the contents of the top row. In this situation, only one cell is selected (the top row of the table that only has one column) and the SpecialCells command applies to the entire sheet instead of the selected range. What was happening to me was other cells on the sheet that were outside of my table were also getting cleared.
I did some digging and found this advice from Mathieu Guindon:
Range SpecialCells ClearContents clears whole sheet
Range({any single cell}).SpecialCells({whatever}) seems to work off the entire sheet.
Range({more than one cell}).SpecialCells({whatever}) seems to work off the specified cells.
If the list/table only has one column (in row 1), this revision will check to see if the cell has a formula and if not, it will only clear the contents of that one cell.
Public Sub ClearList(lst As ListObject)
'Clears a listObject while leaving 1 empty row + formula
' https://stackoverflow.com/a/53856079/1898524
'
'With special help from this post to handle a single column table.
' Range({any single cell}).SpecialCells({whatever}) seems to work off the entire sheet.
' Range({more than one cell}).SpecialCells({whatever}) seems to work off the specified cells.
' https://stackoverflow.com/questions/40537537/range-specialcells-clearcontents-clears-whole-sheet-instead
On Error Resume Next
With lst
'.Range.Worksheet.Activate ' Enable this if you are debugging
If .ShowAutoFilter Then .AutoFilter.ShowAllData
If .DataBodyRange.Rows.Count = 1 Then Exit Sub ' Table is already clear
.DataBodyRange.Offset(1).Rows.Clear
If .DataBodyRange.Columns.Count > 1 Then ' Check to see if SpecialCells is going to evaluate just one cell.
.DataBodyRange.Rows(1).SpecialCells(xlCellTypeConstants).ClearContents
ElseIf Not .Range.HasFormula Then
' Only one cell in range and it does not contain a formula.
.DataBodyRange.Rows(1).ClearContents
End If
.Resize .Range.Rows("1:2")
.HeaderRowRange.Offset(1).Select
' Reset used range on the sheet
Dim X
X = .Range.Worksheet.UsedRange.Rows.Count 'see J-Walkenbach tip 73
End With
End Sub
A final step I included is a tip that is attributed to John Walkenbach, sometimes noted as J-Walkenbach tip 73 Automatically Resetting The Last Cell
I use this code to remove my data but leave the formulas in the top row. It also removes all rows except for the top row and scrolls the page up to the top.
Sub CleanTheTable()
Application.ScreenUpdating = False
Sheets("Data").Select
ActiveSheet.ListObjects("TestTable").HeaderRowRange.Select
'Remove the filters if one exists.
If ActiveSheet.FilterMode Then
Selection.AutoFilter
End If
'Clear all lines but the first one in the table leaving formulas for the next go round.
With Worksheets("Data").ListObjects("TestTable")
.Range.AutoFilter
On Error Resume Next
.DataBodyRange.Offset(1).Resize(.DataBodyRange.Rows.Count - 1, .DataBodyRange.Columns.Count).Rows.Delete
.DataBodyRange.Rows(1).SpecialCells(xlCellTypeConstants).ClearContents
ActiveWindow.SmallScroll Down:=-10000
End With
Application.ScreenUpdating = True
End Sub
I usually use something very simple if you just want to clear table contents.
Sub Clear_table()
Range("Table1").ClearContents
End Sub
Obviously if you have a workbook with multiple pages you might want to change the code to accommodate that.
Sub Clear_table()
Worksheets("Sheet1").Range("Table1").ClearContents
End Sub
If you want to delete the entire table except your headers, and your formula, you can try this:
Sub DeteteTableExceptFormula()
Dim tb As ListObject
Set tb = activeworksheet.ListObjects("MyTable")
tb.DataBodyRange.Delete
End Sub

Resources