Why does rotating elements in the table differ from the rule?

Hello,

I am trying to style a table with the first column being rotated text. I have run into a difference between rotating the text directly in the cells versus using a filtered show rule (#show table.cell.where(x: 0): it => rotate(-90deg, reflow: true)[#strong(it)]), with the former producing substantially nicer looking results:

My first question is: why? This seems like it should be equivalent, but it seems that setting the content and rotating the content are not commutative, which is what I would expect the reflow: true option to enforce.

My next question is: the show rule then nullifies the align keyword in the table, is this intentional?

At the link you can see a show rule (rightmost in the image), which nests the rotation inside an alignment and produces a nice result (perhaps slightly different to the first one?) but still ignores the align table option; this somehow splits the difference, but is also somewhat obscured – is this the preferred method of achieving this layout?

1 Like

I don’t know the exact mechanics of how layout happens here, but the two things are not equivalent: if you put rotate() in a cell, then the cell’s content is rotated. in the show rule you rotate it, which is the whole cell. I would say that in general, the cell should not be rotated. I could e.g. imagine that this leads to the top border actually being the left one; you can test whether that prediction is correct.

You can however (unless there are specific limitations with table cells, which may be the case) write a show rule that replaces the cell’s body. The technique is basically the same as the one used in How to avoid nested enum items breaking at the end of the page? - #2 by SillyFreak or How can I manipulate content values? - #2 by SillyFreak (bottom code sample).

1 Like

Ah – this distinction between rotating the cell content versus rotating the cell is what I had misunderstood. Indeed, unpacking the fields to manipulate the context from within the show rule works well and is pretty legible, here is a solution for anyone interested:

#let tab4 = {
  show table.cell.where(x: 0): it => {
    let (body, ..fields) = it.fields();
    return align(fields.align)[#rotate(-90deg, reflow: true)[#strong(body)]]
  }
  table(
    columns: (2em,1fr,1fr), 
    align: (center+horizon, center+horizon, center+horizon), 
    rows: (2em, (13em,)*3).flatten()
  )[][1][2][Longer title][][][Another Long Title][][][Very long title][][]
}
2 Likes