Skip to content

Conversation

@dereuromark
Copy link
Contributor

@dereuromark dereuromark commented Nov 30, 2025

Summary

This PR adds Creole-style |= table header syntax to djot-php, providing a more flexible way to mark individual cells as headers.

Features

1. Creole-style Header Cells (|=)

Mark individual cells as headers using the |= prefix (must be directly attached to pipe):

|= Name |= Age |
| Alice | 28   |
| Bob   | 34   |

Renders as:

<table>
<tr><th>Name</th><th>Age</th></tr>
<tr><td>Alice</td><td>28</td></tr>
<tr><td>Bob</td><td>34</td></tr>
</table>

2. Cell Alignment Markers

Alignment markers must be directly attached to |= (no space):

Syntax Alignment
|=< text Left
|=> text Right
|=~ text Center

Example:

|=< Left |=~ Center |=> Right |
| A      | B        | C       |

Header alignment propagates to data cells below when no separator row is present.

3. Row Headers

This syntax enables row headers on the left side of tables:

|= Category | Value |
|= Apples   | 10    |
|= Oranges  | 20    |

4. Mixed Header/Data Cells

Mix header and regular cells in the same row:

|= Header | Regular |
| Data    | Data    |

Compatibility Notes

Important: The = must be directly attached to the pipe character:

Input Interpretation
|= text Header cell with content "text"
| = text Regular cell with content "= text"
|=< Left-aligned header
|= < Header with content "< ..."

Additional compatibility:

  • Traditional separator row syntax (|---|) continues to work
  • Separator row alignment takes precedence over |= alignment
  • Works seamlessly with colspan (<), rowspan (^), and multi-line cells (+)

Test Coverage

  • 13 new tests covering all features
  • All 1415 existing tests continue to pass
  • PHPStan passes with no errors

Related

@codecov
Copy link

codecov bot commented Nov 30, 2025

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 93.87%. Comparing base (0b8e068) to head (65f247d).

Additional details and impacted files
@@             Coverage Diff              @@
##             master       #8      +/-   ##
============================================
+ Coverage     93.81%   93.87%   +0.06%     
- Complexity     2049     2067      +18     
============================================
  Files            74       74              
  Lines          5495     5552      +57     
============================================
+ Hits           5155     5212      +57     
  Misses          340      340              

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@dereuromark dereuromark force-pushed the feature/table-header-equals-syntax branch from ad3e8ae to 09c86ed Compare November 30, 2025 04:22
@dereuromark dereuromark added extra beyond standard/specs RFC labels Dec 1, 2025
dereuromark added a commit that referenced this pull request Dec 5, 2025
Addresses TBD items from PR #8:
- Row/column spans using || (colspan) and |^ (rowspan)
- Multi-line cells using trailing \ continuation
- Interaction between |= headers and spanning syntax

All features are strictly opt-in and compatible with original djot specs.
@dereuromark dereuromark force-pushed the feature/table-header-equals-syntax branch from 7080f78 to ea5d384 Compare December 5, 2025 22:14
dereuromark added a commit that referenced this pull request Dec 5, 2025
Implements cell spanning syntax for tables:
- Colspan: || (empty cells) after content spans multiple columns
- Rowspan: |^| continues a cell from the row above
- Header rowspan: |=^ for header cells that span rows

Features:
- TableCell node now has colspan and rowspan properties
- HtmlRenderer outputs colspan/rowspan attributes
- Compatible with |= header syntax from PR #8
- Standard djot tables work unchanged (opt-in extension)

Syntax examples:
- |= Header || (colspan=2)
- |^ | (rowspan continuation)
- |=^ | (header rowspan)
Adds support for marking individual cells as headers using the |= prefix
(Creole/MediaWiki-style syntax). This enables:

- Headers without requiring a separator row
- Mixed header and data cells in the same row
- Row headers on the left side of tables
- Inline alignment markers: |=< (left), |=> (right), |=~ (center)

The marker must be directly attached to the pipe character to be recognized
as a header (|= is header, | = is literal content).

This feature integrates cleanly with the existing table spanning features
(colspan with <, rowspan with ^, and multi-line cells with +).
@dereuromark dereuromark force-pushed the feature/table-header-equals-syntax branch from 25b208c to 4967fca Compare January 20, 2026 06:05
Tests cover:
- Multi-line cells with + continuation
- Cell attributes with {.class}= syntax
- Combined rowspan and colspan
- Rowspan from headers into data rows
- Continuation rows don't create new headers
- Multiple header rows with different alignments
- Row header pattern (first column as headers)
The header marker now comes before attributes for better visual clarity:
- New (preferred): |={.class} Header |
- Combined: |=<{.class} Header | (alignment then attributes)
- Old syntax |{.class}= still works via cell-level attributes

Order: |= [alignment] [{attributes}] content

This keeps |= together as a visual unit, making it clearer that
the cell is a header with optional modifiers.
When using both alignment markers (|=<) and explicit style attributes
({style="..."}), the renderer now properly merges them into a single
style attribute instead of creating duplicate style attributes.

Example: |=<{style="color: red"} text |
Before: style="color: red" style="text-align: left;"
After:  style="text-align: left; color: red"
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

extra beyond standard/specs RFC

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants