Vertical flow is the discipline of making rendered Markdown read cleanly. It optimizes the page the reader sees, not only the source text you type.
| Principle | Outcome |
|---|---|
| Fit the viewport | No horizontal displacement. |
| Stack the hierarchy | The eye always has a next place to land. |
| Chunk one idea | The reader never carries two burdens at once. |
| Anchor with code | Syntax becomes a visual landmark. |
Vertical flow is not sparse text.
Vertical flow is not tables versus lists.
Vertical flow is the combination that gives the best rendered output.
The rendered page is the artifact.
Source formatting matters because it shapes the render.
Rendered clarity wins when source neatness and output quality disagree.
Use the form that makes the page easiest to scan:
| Content Shape | Best Form |
|---|---|
| Compare two axes | Narrow table. |
| Show ordered steps | Numbered list. |
| Group related facts | Bulleted list. |
| Teach syntax | Code block. |
| Mark a section | Colored heading. |
Use this selector when choosing a shape:
function Select-VerticalShape {
param(
[Parameter(Mandatory)]
[ValidateSet('Compare', 'Procedure', 'Group', 'Syntax', 'Warning')]
[string]$ContentKind
)
switch ($ContentKind) {
'Compare' {
'Table'
}
'Procedure' {
'NumberedList'
}
'Group' {
'BulletList'
}
'Syntax' {
'CodeBlock'
}
'Warning' {
'RedLandmark'
}
}
}
The reader should never need horizontal navigation to understand the document.
| Element | Target |
|---|---|
| Headers | 40 to 60 characters. |
| Prose | 60 to 80 characters. |
| Tables | Two or three narrow columns. |
| Lists | One idea per item. |
| Code | As narrow as the syntax allows. |
Long code can exist.
Long prose should not.
Score a draft before calling it done:
$verticalFlowScore = [ordered]@{
HeaderUnderSixty = $true
ProseUnderEighty = $true
TablesAreNarrow = $true
CodeAnchorsSyntax = $true
OneIdeaPerBlock = $true
}
Any $false value is a rewrite signal.
Use repeated landmarks.
Readers learn the page through rhythm.
| Role | Shape |
|---|---|
| Primary section | Gold heading. |
| Supporting idea | Short paragraph. |
| Comparison | Compact table. |
| Procedure | Numbered steps. |
| Syntax | Fenced code block. |
| Warning | Red landmark. |
Keep the same visual role in the same visual shape.
Do not make the reader relearn the page section by section.
Use gold headings as navigation anchors.
<h1 style="color: #DCA657;">🎆 Document Title</h1>
<h2 style="color: #DCA657;">Section Title</h2>
The heading should name the thing.
Do not use decorative headings that hide the content.
Use this section skeleton:
<h2 style="color: #DCA657;">Section Name</h2>
One sentence states the point.
| Signal | Meaning |
| --- | --- |
| Concrete thing | Concrete meaning. |
One sentence closes the block.
Use a table when comparison is the point.
| Signal | Meaning |
| --- | --- |
| Gold heading | Navigation. |
| Code block | Syntax anchor. |
| Blank line | Concept boundary. |
Keep tables narrow.
Prefer two columns.
Use three only when the third column earns its width.
Do not do this:
| Signal | Meaning | Notes | Reader Action |
| --- | --- | --- | --- |
| Gold heading | Navigation | Use everywhere | Scan section starts |
Do this:
| Signal | Meaning |
| --- | --- |
| Gold heading | Navigation. |
Use a list when items belong to one concept.
- one signal
- one meaning
- one action
One item should carry one idea.
If an item needs a paragraph, split the concept.
Do not do this:
- Use headings for navigation, tables for comparison, lists for groups,
and code blocks for syntax because each one solves a different job.
Do this:
- Headings mark navigation.
- Tables compare.
- Lists group facts.
- Code blocks anchor syntax.
Use code blocks when syntax is the thing being taught.
switch ($Task) {
'test' {
Invoke-Pester <test-root>
}
'docs' {
ConvertTo-SharpDown -Path <source-root> -OutPath <output-root> -Recurse
}
}
Code blocks are visual anchors.
They should clarify structure, not decorate the page.
Prefer code that encodes the rule:
if ($Line.Length -gt 80 -and -not $LineIsCode) {
'Rewrite'
}
Avoid code that is only atmospheric:
Write-Host 'Looks clean'
Each block should carry one primary concept.
| Block | Carries |
|---|---|
| Heading | The destination. |
| Paragraph | The claim. |
| Table | The comparison. |
| List | The grouped facts. |
| Code | The syntax. |
Whitespace separates concepts.
Do not use whitespace as decoration.
Use one block per concept:
<h2 style="color: #DCA657;">One Concept</h2>
One claim.
One supporting shape.
One closing sentence.
Move from identity to proof.
| Layer | Purpose |
|---|---|
| One | Name the document. |
| Two | State the rule. |
| Three | Show the pattern. |
| Four | Prove with an example. |
The reader should understand the page before reaching the example.
The example should confirm the rule, not rescue it.
Avoid
Read the rendered page.
Ask these questions:
| Question | Passing Answer |
|---|---|
| Can I read without zooming? | Yes. |
| Can I scroll without losing context? | Yes. |
| Do headings form a map? | Yes. |
| Do tables compare instead of sprawl? | Yes. |
| Do code blocks anchor syntax? | Yes. |
The final test is visual.
If the render looks worse, the source is not done.
Run this review loop:
foreach ($Section in $RenderedDocument.Sections) {
Test-HeaderMap $Section
Test-LineLength $Section
Test-ShapeChoice $Section
Test-ConceptBoundary $Section
}
The names are pseudo-code. The discipline is real.