dir属性对vertical-rl无物理排列影响,但决定光标位置、选词逻辑、标点翻转、连字行为及屏幕阅读器顺序;混合排版必须用隔离方向,dir="auto"在竖排中基本失效。

dir属性对vertical-rl书写模式没有直接作用
dir属性只控制文本的逻辑书写方向(LTR/RTL),不参与writing-mode的轴向定义。设置writing-mode: vertical-rl后,dir="rtl"或dir="ltr"不会改变文字从上到下、从右到左的物理排列——那是writing-mode和text-orientation的事。
但dir仍会影响垂直排版中的关键交互行为,因为Unicode双向算法(UBA)依然运行:
-
<input>光标在垂直文本中仍按逻辑方向起始:若,光标默认停在右侧列首(即视觉顶部偏右),而非左侧 - 双击选词仍基于逻辑顺序:中文竖排里夹一段阿拉伯语,
<bdi></bdi>包裹才能让“مرحبا”被整体选中,否则UBA可能把字母拆开 -
getSelection().getRangeAt(0)返回的startOffset位置,受dir影响,不是纯视觉坐标 - 屏幕阅读器朗读顺序仍由
dir决定,哪怕文字是竖着写的
vertical-rl + dir="rtl"组合的真实效果
这个组合看似冗余,实则常见于阿拉伯语/波斯语竖排古籍数字化场景。它的实际作用不是“翻转垂直方向”,而是激活RTL语境下的标点规则与连字行为:
- 括号自动翻转:
(مرحبا)在dir="rtl"下渲染为)مرحبا(,即使文字是竖排 - 阿拉伯数字(٠١٢٣)保持东阿拉伯形式,而非ASCII数字,
lang="ar"必须同步设置才生效 - 连字符(ـ)和词中形( contextual shaping)正确触发,否则竖排阿拉伯语会断开成孤立字形
-
textarea内换行方向仍按逻辑列推进:按Enter后新行出现在当前行下方,但光标在新行的“逻辑起点”——对dir="rtl"就是右侧列边
错误写法:<div style="writing-mode: vertical-rl; direction: rtl">——<code>direction不触发UBA,括号不翻转,复制粘贴后顺序错乱。
混合排版时在vertical-rl容器里的必要性
当竖排容器中嵌入横排片段(如URL、英文术语、版本号),仅靠writing-mode无法隔离方向逻辑。此时<bdi></bdi>仍是唯一可靠方案:
-
<p style="writing-mode: vertical-rl" dir="rtl">النسخة <bdi>v2.4.1</bdi></p>能确保v2.4.1按LTR逻辑显示,避免被UBA重排成1.4.2v - 不要用
<span dir="ltr"></span>替代<bdi></bdi>:它不创建独立Bidi边界,竖排中仍可能被上方阿拉伯文字“拖拽”方向 - 动态插入内容(如
el.innerHTML = '<bdi>' + url + '</bdi>')必须保留<bdi></bdi>标签,DOM解析后才会触发UBA重算 - 旧版Android WebView对
<bdi></bdi>在vertical-rl中支持不稳定,需降级为<bdo dir="ltr"></bdo>(仅限调试,因<bdo></bdo>强制重排,会把123变成321)
dir="auto"在vertical-rl环境里几乎必然失效
dir="auto"依赖首个强方向字符判断逻辑方向,但在竖排场景下,这个机制基本瘫痪:
- 竖排中文开头(如“第一章”):中文字符无强方向性 → fallback 到父级
dir值,不会识别为LTR - 竖排阿拉伯语开头但含前导空格或换行符 → 首字符识别失败,强制
ltr,导致括号反向、光标错位 - 服务端渲染时,竖排容器HTML已生成,JS动态填入阿拉伯文本,
dir="auto"不会重新触发方向推断 - Safari对竖排+
dir="auto"的组合支持极差,常将整列判为LTR,连lang="ar"都救不回来
真正难的不是让文字竖起来,而是让浏览器在竖排时仍能正确理解“这段话该从哪边开始读、标点该往哪边包、用户按退格键该删哪个字”——这些全靠dir和lang在底层协同,而不是CSS看起来像不像。











