@Adam has posted the correct answer for this using CSS methods.
If you are looking to manually solve this through data manipulation, then this is a solution for you.
export class UsersComponent {
// Your data
group: Array<string> = ['A', 'B', 'C', 'D'];
// Fixed number of rows
rows: number = 3;
// Calculate number of columns based on data length and required number of rows
columns: number = Math.ceil(this.group.length / this.rows);
// We will push data here
data: any = [];
constructor() {
// counter for data
let elem = 0;
// Outer loop
for (let i = 0; i < this.columns; ++i) {
// Create a row in data
this.data.push([]);
// Inner Loop
for (let j = 0; j < this.rows; ++j) {
// Do not push undefined elements (if any)
if (this.group[elem]) {
this.data[i][j] = this.group[elem];
}
// increment counter
elem++;
}
}
// We got the data, now lets take the transpose to invert it.
this.data = this.transpose(this.data);
console.log(this.data);
}
// Credits: https://stackoverflow.com/questions/17428587/transposing-a-2d-array-in-javascript
transpose(matrix: any) {
return matrix[0].map((col: any, i: any) =>
matrix.map((row: any) => row[i])
);
}
}
Now that we have data in 2d format (with correct number of rows and columns), you can display it in your HTML like:
<table class="table">
<tr *ngFor="let row of data">
<span *ngFor="let column of row">
<td *ngIf="column">{{ column }}</td>
</span>
</tr>
</table>
It is possible to change ordering of elements appearing in a row (populate row first or populate columns first) just by tweaking outer and inner loops in code. Also you can change number of rows and size of your data to test it for various cases.
Demo here https://stackblitz.com/edit/angular-mgte7k?file=src%2Fusers%2Fusers.component.ts