excelvba

Excel Horizontal to Vertical Groups VBA


Please see here for my original question and the VBA code I'm using.

I recently asked for help converting a Vertical Table into a Horizontal Table while preserving Groups. Now I need to convert the Horizontal Table (that has been modified) back to the Vertical Table.

The Horizontal Table is (Table 1 below) and has a single Header

TABLE 1

enter image description here

I need to convert Table 1 back to this:

TABLE 2

enter image description here


Solution

  • Sub Hor2Ver()
        Dim i As Long, j As Long, r As Long, iR As Long, arrRes(), arrData
        Const HEADER_CNT = 1
        Const SRC_SHT = "Sheet8"  ' update sheetname as needed
        Const DEST_SHT = "Master"
        Dim srcSht As Worksheet: Set srcSht = Sheets(SRC_SHT)
        Dim ColCnt As Long
        ' get the columns count of a sub-table / data block
        Dim mergeSht As Worksheet: Set mergeSht = Sheets(DEST_SHT)
        Const START_COL_DEST = 1 ' or "A"
        Const KEY_ROW = 2
        ' Get the columns count from the 2nd row in Table2 (dest. table)
        ColCnt = mergeSht.Cells(KEY_ROW, 1).End(xlToRight).Column
        Dim dataRng As Range: Set dataRng = srcSht.UsedRange
        If dataRng.Cells(1).Column = 1 Then ' skip the first col on src table
            Set dataRng = dataRng.Offset(, 1)
        End If
        arrData = dataRng.Value
        ReDim arrRes(1 To UBound(arrData, 2) / ColCnt * UBound(arrData, 1), 1 To ColCnt)
        For i = LBound(arrData, 2) To UBound(arrData, 2) Step ColCnt + 1 ' loop through each block
            For r = LBound(arrData) + HEADER_CNT To UBound(arrData) ' loop through rows
                If Len(arrData(r, i)) = 0 Then Exit For
                iR = iR + 1
                For j = 1 To ColCnt ' load a row
                    arrRes(iR, j) = arrData(r, i + j - 1)
                Next
            Next
        Next
        If iR = 0 Then
            MsgBox "Can't find table(s) on sheet " & srcSht.Name
        Else
            Dim targetCell As Range
            Set targetCell = mergeSht.Cells(mergeSht.Rows.Count, START_COL_DEST).End(xlUp)
            If Len(targetCell.Value) > 0 Then
                Set targetCell = targetCell.Offset(1)
            End If
            targetCell.Resize(iR, ColCnt).Value = arrRes
        End If
    End Sub
    

    enter image description here