Home » excel » vba – Excel 2003: Programmatic sort of sheet in different workbook

vba – Excel 2003: Programmatic sort of sheet in different workbook

Posted by: admin May 14, 2020 Leave a comment

Questions:

From the current workbook, I want to open a sheet in the source workbook, turn off any filtering that may be present, sort by one column, then another, then another. Am getting 1004 and other errors. This needs to run on 2003. Any help will be appreciated!

Dim WB As Workbook, WasWBOpen As Boolean, srcfile As String, srcpath As String,    
onecol as integer, twocol as integer, thrcol as integer

srcpath = "blahblah"
srcfile = "blah.xls"

On Error Resume Next
Set WB = Workbooks(srcfile)
WasWBOpen = True
On Error GoTo 0
If WB Is Nothing Then
Set WB = Workbooks.Open(srcpath & srcfile, UpdateLinks:=False)
WasWBOpen = False
End If

'code before this opens source wkbook

lstrow = Worksheets("Sheet1").UsedRange.Row - 1 + Worksheets("Sheet1").UsedRange.Rows.Count
lstcol = Worksheets("Sheet1").UsedRange.Column - 1 + Worksheets("Sheet1").UsedRange.Columns.Count

onecol=3
twocol=5
thrcol=8

With WB.Sheets("Sheet1")

.AutoFilterMode = False
.Range("1:1").AutoFilter
'Here's where error occurs--
.Range(Cells(1, 1), Cells(lstrow, lstcol)).Sort _
    Key1:=Columns(onecol), Order1:=xlAscending, _
    Key2:=Columns(twocol), Order2:=xlAscending, _
    Key3:=Columns(thrcol), Order3:=xlAscending, Header:=xlYes

End With

If WasWBOpen = False Then
WB.Close
End If
How to&Answers:
.Range(Cells(1, 1), Cells(lstrow, lstcol)).Sort _ 

is better written as:

.Range(.Cells(1, 1), .Cells(lstrow, lstcol)).Sort _ 

Answer:

The only thing I can make a stab at is perhaps your selection does not include columns 3, 5 or 8. What are the values of lstrow and lstcol before the error?

Answer:

In my experience you can only sort the active worksheet. Try adding .Activate after WB.Sheets("Sheet1").

Information about the last sort is stored against the worksheet. I sometimes suspect this is the problem rather than the sheet to be sorted not being active. But .Activate has always worked for me and so I have never investigated further.

Extra information

I had assumed it was the Sort that generated the error but it is the AutoFilter.

I can generate a 1004 error by leaving row 1 empty.

What purpose does the AutoFilter statement serve? With AutoFilterMode = False I would expect it to return Nothing. Why not delete this statement?

I am also concerned about the range you are sorting. You are subtracting the number of unused rows at the top and unused columns on the left to calculate lstrow and lstcol but then including those unused rows and columns in the sort. The result is that rows at the bottom and columns on the right would not be sorted.

If have not got any unused rows at the top and unused columns on the left, this will not matter but you need to decide which range you want to sort.

Extra information 2

This section was added after I discovered a fourth way of breaking the original code. The following code appears to be bomb-proof.

Option Explicit
Sub TestSort2()

Dim WB As Workbook, WasWBOpen As Boolean, srcfile As String, srcpath As String
Dim onecol As Integer, twocol As Integer, thrcol As Integer

' Undeclared or new variables

Dim InxWB As Long
Dim lstrow As Long
Dim lstcol As Long
Dim srcpathfile As String

' Report the name of the active workbook
Debug.Print "Original active workbook " & ActiveWorkbook.Name

' I created two workbooks named "Failed sort 1.xls" and "Failed sort 2.xls".
' Both are in the same directory. "Failed sort 1.xls" contains this macro.
' "Failed sort 2.xls" contains the data.
srcpath = Application.ActiveWorkbook.Path
srcfile = "Failed sort 2.xls"

srcpathfile = srcpath & "\" & srcfile

WasWBOpen = False
' Check the open workbook for srcfile
For InxWB = 1 To Workbooks.Count
  If Workbooks(InxWB).Name = srcfile Then
    ' Required workbook already open
    Set WB = Workbooks(InxWB)
    WB.Activate                     ' Activate it
    WasWBOpen = True
    Exit For
  End If
Next
If Not WasWBOpen Then
  ' Files was not open
  If Dir(srcpathfile) <> "" Then
    ' File exists
    ' Do you need UpdateLinks:=False?  If there are links
    ' with the sort be affected if they are not updated? 
    Set WB = Workbooks.Open(srcpathfile, UpdateLinks:=False)
  Else
    ' File does not exist
    Call MsgBox(srcpathfile & " does not exist", vbOKOnly)
    Exit Sub
  End If
End If

' WB is now the active workbook whether it was open before or not
Debug.Print "Final active workbook " & ActiveWorkbook.Name      ' Confirm

With Sheets("Sheet1")
  .Activate
  .AutoFilterMode = False

  ' Get the last used row and cell of the worksheet
  lstrow = Cells.SpecialCells(xlCellTypeLastCell).Row
  lstcol = Cells.SpecialCells(xlCellTypeLastCell).Column

  onecol = 3
  twocol = 5
  thrcol = 8

  If onecol > lstcol Or twocol > lstcol Or thrcol > lstcol Then
    Call MsgBox("The sort range does include the sort columns", vbOKOnly)
    If Not WasWBOpen Then
      Close
    End If
    Exit Sub
  End If

  Range(Cells(1, 1), Cells(lstrow, lstcol)).Sort _
        Key1:=Columns(onecol), Order1:=xlAscending, _
        Key2:=Columns(twocol), Order2:=xlAscending, _
        Key3:=Columns(thrcol), Order3:=xlAscending, Header:=xlYes
End With

If Not WasWBOpen Then
  Close
End If

End Sub