Excel VBA: Color Rows if Column is Sorted

gertie193

Board Regular
Joined
Feb 28, 2008
Messages
82
Hello,

I am working in Excel 2013 and trying to color rows of a used range automatically after column G (US column) or I (DS column) is sorted. Another user will be having to sort (sort either desc or asc, it will vary) between these 2 columns over and over and I need to rows to be colored automatically after each sort. They don't want to push a button to color the rows after each sort.

tonyyy helped me some weeks ago do something similar with the code I have below. He added the parts I've designated '<==HERE' to color rows after a button was pushed to hide & unhide rows that contained certain text in a certain column (I've removed the button code to hide and unhide).

I'm sure all I need to do is replace his code where it says '<==HERE' with code to test as follows:

Code:
If column G is sorted or column I is sorted Then
, and then proceed with the code to color the rows.

Problem:
I just don't know how to test if a column is sorted.

I've seen some posts using a formula and one using a loop to go through each cell to see if it is sorted comparing to the cell above, but the sort we have will vary between ascending and descending in either columns G and I. Also, I didn't know if those are efficient ways to do it or if there is another way.

FYI:
Columns G and I are numerical values but I don't remember if they export as text. This data is exported from the web to Excel. (The example wkbook via this link on Google Drive shows the columns G and I as text with the code below in the Color_BySort module: Color based on Sort.xlsm - Google Drive )

I would appreciate any help, even if you could lead me in the right direction. Thank you in advance.

Code:
Sub ColorBySort()
'Color report based on Sort by US column (G) or DS Column (I)
'NOT FINISHED


Application.ScreenUpdating = False


Dim colorrng As Range
Dim rng As Range
Dim r As Long
Dim lastrow As Long
Dim colourIt As Boolean
Dim colour As XlColorIndex


'*******Set colourit variable for Color Rows code***********
lastrow = Cells(Rows.Count, "B").End(xlUp).Row
colourIt = False
Set colorrng = Range("A1:L" & lastrow).SpecialCells(xlCellTypeVisible)


'*******Set rng variable for sort Rows code***********
Set rng = Range("G2:G" & lastrow)


'*******COLOR ROWS CODE***********
With ActiveSheet


        r = 2  ' First row of data on row 2
        'clears any coloring from before
        Range("A2:M" & lastrow).Interior.Color = xlColorIndexNone


        Do While .Cells(r, "B").Value <> ""
            'See if value has changed - highlight by Service within each hub - "B" is Service column
            'Must arrange data so that "B" is Svc Group column
            If Rows(r).Hidden = False Then '[B]<====HERE[/B]
                If .Cells(r, "B").Value <> .Cells(r - 1, "B").Value Then
                    colourIt = Not colourIt
                End If
            End If


            'Determine which colour to use on this row
            If colourIt Then
                colour = RGB(217, 225, 242)
            Else
                colour = xlColorIndexNone
            End If
            'Apply the colouring - starting in row r = 2 and column "A"
            If Rows(r).Hidden = False Then '[B]<====HERE[/B]
                .Range(.Cells(r, "A"), .Cells(r, .Cells(r, .Columns.Count).End(xlToLeft).Column)).SpecialCells(xlCellTypeVisible).Interior.Color = colour
                'colorrng.Rows(r).Interior.Color = colour
            End If


            'Point to the next row of data
            r = r + 1
        Loop
        
End With
    
    
Application.ScreenUpdating = True


On Error GoTo 0


End Sub
 
Last edited:

Excel Facts

Ambidextrous Undo
Undo last command with Ctrl+Z or Alt+Backspace. If you use the Undo icon in the QAT, open the drop-down arrow to undo up to 100 steps.
Here's a routine that will test a list to see if it is sorted. Perhaps you can adapt it to your code.
Code:
Sub IsListSorted()
Dim R As Range, Arr As Object, i As Long, ArrSa As Object, ArrSd As Object
Set R = Range("I2:I12")  'set the range holding the list here - exclude header if any
Set Arr = CreateObject("System.Collections.ArrayList")
'populate Arr
For Each c In R
       Arr.Add c.Value
Next c
Set ArrSa = Arr.Clone
ArrSa.Sort
Set ArrSd = Arr.Clone
ArrSd.Sort
ArrSd.Reverse
For i = 0 To UBound(Arr.toarray())
       If ArrSa.toarray()(i) <> Arr.toarray()(i) Then
              MsgBox "Not sorted ascending"
              Exit For
       Else
              If i = UBound(Arr.toarray()) Then
                     MsgBox "Sorted ascending"
                     GoTo Xit
              End If
       End If
Next i
For i = 1 To UBound(Arr.toarray())
       If ArrSd.toarray()(i) <> Arr.toarray()(i) Then
              MsgBox "Not sorted descending"
              Exit For
       Else
              If i = UBound(Arr.toarray()) Then
                     MsgBox "Sorted descending"
                     GoTo Xit
              End If
       End If
Next i

Xit:
End Sub
 
Last edited:
Upvote 0
Thank you for the code. I found a code that I understand better since I am learning VBA, and the new line in VBA I’ve added is:

Code:
If Evaluate("SUMPRODUCT(--(G2:G" & lastrow - 1 & ">G3:G" & lastrow & "))") Then

It is equal to the worksheet function, SUMPRODUCT(--(G2:G17>G3:G18)), which works as a function in the worksheet.

I mentioned that the data will be sorted asc or desc, but this data will only be sorted large to small (desc) between the G column and I columns at different times.

Problems:
1. This works so the rows are colored but only when you sort the G column the first time.
a. if you then sort column I (using the sort dialog box or the sort under the filter arrows), the rows will not be colored correctly so that the rows are colored at every change in column B. You can, however, run the code from within VBA and it will color column I correctly.
b. if you then go back to sort column G, the rows will be colored correctly like the first time.
c. but if you change a value in column B to see if that row will be colored properly when you sort I and go back to sort G, it will not color the row of that new value in column B.

I’ve tried:
1. Adding code to cover column I but nothing happens when I sort. In fact, any coloring on the rows disappears.
2. Adding >0 to the end of the new line so that:
Code:
 If Evaluate("SUMPRODUCT(--(G2:G" & lastrow - 1 & ">G3:G" & lastrow & "))") > 0 Then
But after thinking about it I don’t think that does anything.

Can you/anyone help me further toward the solution to color the rows after column G or I is sorted descending? I appreciate you/anyone's help.

Code:
Sub ColorNCMSBySort()
'Color NCMS report based on Sort by USC column or DSC Column
'NOT FINISHED
 
Application.ScreenUpdating = False
 
Dim colorrng As Range
Dim rng As Range
Dim r As Long
Dim lastrow As Long
Dim colourIt As Boolean
Dim colour As XlColorIndex
 
'*******Set colourit variable for Color Rows code***********
lastrow = Cells(Rows.Count, "B").End(xlUp).Row
colourIt = False
Set colorrng = Range("A1:L" & lastrow).SpecialCells(xlCellTypeVisible)
 
'*******Set rng variable for Column that the sort is based on***********
Set rng = Range("G2:G" & lastrow)
 
'*******COLOR ROWS CODE***********
With ActiveSheet
 
        r = 2  ' First row of data on row 2
        'clears any coloring from before
        Range("A2:L" & lastrow).Interior.Color = xlColorIndexNone
 
        Do While .Cells(r, "B").Value <> ""
            'See if value has changed - highlight by Service within each Home - "B" is Service column
            'Must arrange data so that "B" is Svc Group column
            If Evaluate("SUMPRODUCT(--(G2:G" & lastrow - 1 & ">G3:G" & lastrow & "))") Then '<====HERE
                If .Cells(r, "B").Value <> .Cells(r - 1, "B").Value Then
                    colourIt = Not colourIt
                End If
            End If
'            If Evaluate("SUMPRODUCT(--(I2:i" & lastrow - 1 & ">i3:i" & lastrow & "))") Then '<====TRIED ADDED CODE FOR COLUMN I
'                 If .Cells(r, "B").Value <> .Cells(r - 1, "B").Value Then
'                    colourIt = Not colourIt
'                 End If
'            End If
 
            'Determine which colour to use on this row
            If colourIt Then
                colour = RGB(217, 225, 242)
            Else
                colour = xlColorIndexNone
            End If
            'Apply the colouring - starting in row r = 2 and column "A"
            If Evaluate("SUMPRODUCT(--(G2:G" & lastrow - 1 & ">G3:G" & lastrow & "))") Then '<====HERE
                .Range(.Cells(r, "A"), .Cells(r, .Cells(r, .Columns.Count).End(xlToLeft).Column)).SpecialCells(xlCellTypeVisible).Interior.Color = colour
                'colorrng.Rows(r).Interior.Color = colour
            End If
'            If Evaluate("SUMPRODUCT(--(I2:i" & lastrow - 1 & ">i3:i" & lastrow & "))") Then '<====TRIED ADDED CODE FOR COLUMN I
 
'                   .Range(.Cells(r, "A"), .Cells(r, .Cells(r, .Columns.Count).End(xlToLeft).Column)).SpecialCells(xlCellTypeVisible).Interior.Color = colour
'            End If
            'Point to the next row of data
            r = r + 1
        Loop
 
End With
 
Application.ScreenUpdating = True
 
On Error GoTo 0
 
End Sub
 
Last edited:
Upvote 0
Hello,

I just wanted to follow up to see if anyone can help/lead me in the right direction after my last attempt posted above. I haven't looked at it since b/c I researched quite a bit to get it to that point.

I'm not that advanced to adapt JoeMo's code that he kindly provided.

I don't want to post too many times after reading the rules, so I will just post this and stop after that.

Thank you for all of your help.

*Correction to code in my last reply* 2 of the comment lines should read:

Code:
[COLOR=#333333]If Evaluate("SUMPRODUCT(--(I2:i" & lastrow - 1 & ">i3:i" & lastrow & "))") Then '<====[B]TRIED ADDING CODE HERE TO SORT FOR COLUMN I[/B][/COLOR]

This line repeats a 2nd time toward the end of the code. But, as I mentioned, with or without this line, the code doesn't work properly--no error, just doesn't work properly to color my rows after I sort column G, then color my rows after I sort column I.
 
Last edited:
Upvote 0
If you want this to run automatically, without needing to push a button or run code, I'd suggest Conditional Formatting. Select columns G and I, click Conditional Formatting > New Rule > Use a Formula, and enter:

=AND(ROW()>1,G1<>"",SUMPRODUCT(--(OFFSET(G$2,0,0,COUNTA(G:G)-2)<=OFFSET(G$3,0,0,COUNTA(G:G)-2)))=COUNTA(G:G)-2)
select a fill color for ascending.

Repeat with the same formula, changing the red <= to >= and select a fill color for descending. Now the columns will highlight one color or the other when it is sorted, or no color when it's not sorted. This assumes a title row, and at least 2 values. It works automatically when data is added, or you sort the column.
 
Upvote 0
Thank you for your answer, but I just realized I made a major omission. It's in my code, but I didn't detail it out in my question. I need Excel to color my used range when I sort column G or to color my rows after I sort column I; HOWEVER, at every change in value in column B.

I know I tested your conditional formatting which colors the whole column of G and I.

For you or others who might post an answer I have posted an example of what the finished data would look like with just Column G sorted descending below. I would then want to sort column I descending and have the rows colored appropriately:

The rows in bold would be colored rows and the non-bold rows are not colored because the value in Column B has changed. The Column F is column F in the example but really column B in my code.

Column F (B)Column G ItemColumn I Item Item
five123.name.state
44
asdfsa
25
asdfsa
asdfsa
five123.name.state
29
asdfsa
57
asdfsa
asdfsa
appl444.name. state 23asdfsa 25 asdfsaasdfsa
grif555.name.state
22
asdfsa
8
asdfsa
asdfsa
jar777.name.state 21asdfsa 14 asdfsaasdfsa
hat888.name.state
13
asdfsa
93
asdfsa
asdfsa

<tbody>
</tbody>



I apologize to you Eric and you all for not being clear. I appreciate any help if it is re: code (or conditional formatting).
 
Last edited:
Upvote 0
Conditional Formatting doesn't much like Sorting, but try this (still using Conditional Formatting).

1. Remove any existing CF
2. In column L, leave cell L1 empty, put the formula shown in L2 and copy down to the end of the data.
3. Select F2:L?? and apply the CF formula shown (choose your own formatting)
4. Remove the AutoFilter from the sheet and re-apply it to include column L
5. Hide column L if you want
6. Test

Excel Workbook
FGHIJKL
1Column F (B)Column GItemColumn IItemItem
2five123.name.state44asdfsa25asdfsaasdfsa1
3five123.name.state29asdfsa57asdfsaasdfsa1
4appl444.name. state23asdfsa25asdfsaasdfsa0
5grif555.name.state22asdfsa8asdfsaasdfsa1
6jar777.name.state21asdfsa14asdfsaasdfsa0
7hat888.name.state13asdfsa93asdfsaasdfsa1
CF with sorting
Cells with Conditional Formatting
CellConditionCell FormatStop If True
L21. / Formula is =INDEX($L:$L,ROW())Abc



Here is my sheet after sorting descending on column I

Excel Workbook
FGHIJKL
1Column F (B)Column GItemColumn IItemItem
2hat888.name.state13asdfsa93asdfsaasdfsa1
3five123.name.state29asdfsa57asdfsaasdfsa0
4five123.name.state44asdfsa25asdfsaasdfsa0
5appl444.name. state23asdfsa25asdfsaasdfsa1
6jar777.name.state21asdfsa14asdfsaasdfsa0
7grif555.name.state22asdfsa8asdfsaasdfsa1
CF with sorting
Cells with Conditional Formatting
CellConditionCell FormatStop If True
 
Last edited:
Upvote 0
Conditional Formatting doesn't much like Sorting, but try this (still using Conditional Formatting).

1. Remove any existing CF
2. In column L, leave cell L1 empty, put the formula shown in L2 and copy down to the end of the data.
3. Select F2:L?? and apply the CF formula shown (choose your own formatting)
4. Remove the AutoFilter from the sheet and re-apply it to include column L
5. Hide column L if you want
6. Test

CF with sorting

FGHIJKL
1Column F (B)Column GItemColumn IItemItem
2five123.name.state44asdfsa25asdfsaasdfsa1
3five123.name.state29asdfsa57asdfsaasdfsa1
4appl444.name. state23asdfsa25asdfsaasdfsa0
5grif555.name.state22asdfsa8asdfsaasdfsa1
6jar777.name.state21asdfsa14asdfsaasdfsa0
7hat888.name.state13asdfsa93asdfsaasdfsa1

<colgroup><col style="font-weight:bold; width:30px; "><col style="width:139px;"><col style="width:77px;"><col style="width:57px;"><col style="width:70px;"><col style="width:57px;"><col style="width:57px;"><col style="width:56px;"></colgroup><tbody>
</tbody>

Spreadsheet Formulas
CellFormula
L2=IF(F2=F1,L1,1-L1)

<tbody>
</tbody>

<tbody>
</tbody>

Conditional formatting
CellNr.: / ConditionFormat
L21. / Formula is =INDEX($L:$L,ROW())Abc

<tbody>
</tbody>

<tbody>
</tbody>


Excel tables to the web >> Excel Jeanie HTML 4


Here is my sheet after sorting descending on column I

CF with sorting

FGHIJKL
1Column F (B)Column GItemColumn IItemItem
2hat888.name.state13asdfsa93asdfsaasdfsa1
3five123.name.state29asdfsa57asdfsaasdfsa0
4five123.name.state44asdfsa25asdfsaasdfsa0
5appl444.name. state23asdfsa25asdfsaasdfsa1
6jar777.name.state21asdfsa14asdfsaasdfsa0
7grif555.name.state22asdfsa8asdfsaasdfsa1

<colgroup><col style="font-weight:bold; width:30px; "><col style="width:139px;"><col style="width:77px;"><col style="width:57px;"><col style="width:70px;"><col style="width:57px;"><col style="width:57px;"><col style="width:56px;"></colgroup><tbody>
</tbody>

Conditional formatting
CellNr.: / ConditionFormat

<tbody>
</tbody>

<tbody>
</tbody>


Excel tables to the web >> Excel Jeanie HTML 4

Thank you, Peter. It works. I will just use conditional formatting instead of VBA.

Maybe if I find out the answer to the VBA version, I will post it here. Thank you, again. I appreciate the help (and the reference to Excel Jeanie).
 
Upvote 0
Thank you, Peter. It works. I will just use conditional formatting instead of VBA ... Thank you, again. I appreciate the help (and the reference to Excel Jeanie).
You are welcome. :)

BTW, best not to fully quote long posts as it makes the thread harder to read/navigate and just occupies storage space needlessly. If you want to quote, quote small, relevant parts only.
 
Upvote 0

Forum statistics

Threads
1,221,310
Messages
6,159,173
Members
451,543
Latest member
cesymcox

We've detected that you are using an adblocker.

We have a great community of people providing Excel help here, but the hosting costs are enormous. You can help keep this site running by allowing ads on MrExcel.com.
Allow Ads at MrExcel

Which adblocker are you using?

Disable AdBlock

Follow these easy steps to disable AdBlock

1)Click on the icon in the browser’s toolbar.
2)Click on the icon in the browser’s toolbar.
2)Click on the "Pause on this site" option.
Go back

Disable AdBlock Plus

Follow these easy steps to disable AdBlock Plus

1)Click on the icon in the browser’s toolbar.
2)Click on the toggle to disable it for "mrexcel.com".
Go back

Disable uBlock Origin

Follow these easy steps to disable uBlock Origin

1)Click on the icon in the browser’s toolbar.
2)Click on the "Power" button.
3)Click on the "Refresh" button.
Go back

Disable uBlock

Follow these easy steps to disable uBlock

1)Click on the icon in the browser’s toolbar.
2)Click on the "Power" button.
3)Click on the "Refresh" button.
Go back
Back
Top