有没有办法强制使用CSS使字体等宽?
我的意思是,使用非等宽字体,你可以强制浏览器以固定的宽度呈现每个字符吗?
答案 0 :(得分:20)
如果这是用于对齐表格中的数字,其中某些字体(使用传统排版)默认使用可变宽度渲染它们(例如Windows上的Segoe UI),您应该查看CSS属性:
font-variant-numeric: tabular-nums;
(这会禁用至少由OpenType字体支持的proportional-nums
变体的numeric-spacing
默认值,并且可能禁用您的特定平台的Web浏览器的文本渲染器支持的其他字体格式< / p>
不需要javascript!这是禁用这些字体中可变宽度字形的最简洁方法,并强制它们使用表格数字(这通常使用相同字体的相同字形,但它们的前导和尾随间隙增加,因此从0到10的10位数字9将以相同的宽度呈现;但是某些字体可能会避免视觉变量interdigit间距,并略微隐藏一些数字,或者可以将底部衬线添加到数字1的脚。
请注意,这并不会禁用使用Segoe UI观察到的变量高度(例如,某些数字将仅为x高度,只有小写字母,其他数字将有上升或下降)。使用
也可以使用CSS禁用这些传统的数字形式 font-variant-numeric: lining-nums;
(这会禁用至少由OpenType字体支持的oldstyle-nums
变体的默认numeric-figure
值,以及您的特定平台的Web浏览器的文本渲染器可能支持的其他字体格式< / p>
您可以将两者结合起来:
font-variant-numeric: tabular-nums lining-nums;
下面的代码片段使用单个比例字体(不是等宽字体!)来演示这一点,该字体具有数字形状变体,例如Windows上的“Segoe UI”,并显示生成的不同水平和垂直对齐。
请注意,如果应用粗体或斜体等不同的样式而不是中等罗马字体,则此样式不会禁止数字更改宽度,如下所示,因为这些将使用不同的字体及其自己的不同指标(这不是所有的保证等宽字体)。
html { font-family: 'Segoe UI'; /* proportional with digit variants */ }
table { margin: 0; padding: 0; border: 1px solid #AAA; border-collapse: collapse; }
th, td { vertical-align:top; text-align:right; }
.unset { font-variant-numeric: unset; }
.traditional { font-variant-numeric: proportional-nums oldstyle-nums; }
.lining { font-variant-numeric: proportional-nums lining-nums; }
.tabular-old { font-variant-numeric: tabular-nums oldstyle-nums; }
.tabular-new { font-variant-numeric: tabular-nums lining-nums; }
.normal { font-variant-numeric: normal; }
<table>
<tr><th>unset<td><table width="100%" class="unset">
<tr><td>Rs12,34,56,789.00/Gal<td><i>Difference Rs86,41,97,532.11/Gal
<tr><td>Rs98,76,54,321.11/Gal<td><b>Total Rs1,11,11,11,110.11/Gal
</table>
<tr><th>traditional<td><table width="100%" class="traditional">
<tr><td>Rs12,34,56,789.00/Gal<td><i>Difference Rs86,41,97,532.11/Gal
<tr><td>Rs98,76,54,321.11/Gal<td><b>Total Rs1,11,11,11,110.11/Gal
</table>
<tr><th>lining<td><table width="100%" class="lining">
<tr><td>Rs12,34,56,789.00/Gal<td><i>Difference Rs86,41,97,532.11/Gal
<tr><td>Rs98,76,54,321.11/Gal<td><b>Total Rs1,11,11,11,110.11/Gal
</table>
<tr><th>tabular-old<td><table width="100%" class="tabular-old">
<tr><td>Rs12,34,56,789.00/Gal<td><i>Difference Rs86,41,97,532.11/Gal
<tr><td>Rs98,76,54,321.11/Gal<td><b>Total Rs1,11,11,11,110.11/Gal
</table>
<tr><th>tabular-new<td><table width="100%" class="tabular-new">
<tr><td>Rs12,34,56,789.00/Gal<td><i>Difference Rs86,41,97,532.11/Gal
<tr><td>Rs98,76,54,321.11/Gal<td><b>Total Rs1,11,11,11,110.11/Gal
</table>
<tr><th>normal<td><table width="100%" class="normal">
<tr><td>Rs12,34,56,789.00/Gal<td><i>Difference Rs86,41,97,532.11/Gal
<tr><td>Rs98,76,54,321.11/Gal<td><b>Total Rs1,11,11,11,110.11/Gal
</table>
</table>
参考:https://developer.mozilla.org/fr/docs/Web/CSS/font-variant-numeric
答案 1 :(得分:11)
你不能用CSS做到这一点。即使你可以,结果也会很糟糕:
如果您确实需要这样做,可以使用JavaScript将每个字符包装在一个元素中(或者只是手工完成):
function wrap_letters($element) {
for (var i = 0; i < $element.childNodes.length; i++) {
var $child = $element.childNodes[i];
if ($child.nodeType === Node.TEXT_NODE) {
var $wrapper = document.createDocumentFragment();
for (var i = 0; i < $child.nodeValue.length; i++) {
var $char = document.createElement('span');
$char.className = 'char';
$char.textContent = $child.nodeValue.charAt(i);
$wrapper.appendChild($char);
}
$element.replaceChild($wrapper, $child);
} else if ($child.nodeType === Node.ELEMENT_NODE) {
wrap_letters($child);
}
}
}
wrap_letters(document.querySelectorAll('.boxes')[0]);
wrap_letters(document.querySelectorAll('.boxes')[1]);
&#13;
.char {
outline: 1px solid rgba(255, 0, 0, 0.5);
}
.monospace .char {
display: inline-block;
width: 15px;
text-align: center;
}
&#13;
<h2 class="boxes">This is a title</h2>
<h2 class="boxes monospace">This is a title</h2>
&#13;
答案 2 :(得分:11)
为什么不在盒子外面和桌子内思考:
<table cellpadding="0" cellspacing="0">
<tr><td>T</td><td>h</td><td>e</td><td></td><td>r</td><td>a</td><td>i</td><td>n</td><td></td><td>i</td><td>n</td><td></td><td>S</td><td>p</td><td>a</td><td>i</td><td>n</td><td></td><td>s</td><td>t</td><td>a</td><td>y</td><td>s</td></tr>
<tr><td>m</td><td>a</td><td>i</td><td>n</td><td>l</td><td>y</td><td></td><td>i</td><td>n</td><td></td><td>t</td><td>h</td><td>e</td><td></td><td>p</td><td>l</td><td>a</td><td>i</td><td>n</td><td>s</td><td>.</td></tr>
</table>
答案 3 :(得分:3)
不,没有办法在CSS中强制执行任何操作。甚至没有办法建议将非等宽字体呈现为等宽字体。
答案 4 :(得分:2)
嗯,你没有说只使用 CSS。只需要一点点Javascript就可以用span
包装每个字母。剩下的就是CSS ......
window.onload = function() {
const secondP = document.getElementById('fixed');
const text = secondP.innerText;
const newText = text.split('').map(c => {
const span = `<span>${c}</span>`;
return span;
}).join('');
secondP.innerHTML = newText;
}
&#13;
p {
position: relative;
border: 1px solid black;
border-radius: 1em;
padding: 1em;
margin: 3em 1em;
}
p::after {
content: attr(name);
display: block;
background-color: white;
color: green;
padding: 0 0.5em;
position: absolute;
top: -0.6em;
left: 0.5em;
}
#fixed span {
display: inline-block;
width: 1em;
text-align: center;
}
&#13;
<p id="variable" name="Variable Width">It might not look nice, but with a little Javascript, I can force a variable width font to act like a fixed-width font.</p>
<p id="fixed" name="Fixed Width">It might not look nice, but with a little Javascript, I can force a variable width font to act like a fixed-width font.</p>
&#13;
在带有常规文本的段落中,它看起来很糟糕,但有些情况下这是有道理的。图标字体和Unicode符号都可以使用这种技术。
我在尝试找到Unicode符号的解决方案时发现了这个问题,这些符号在将常规文本替换为其他Unicode符号时向右移动。
答案 5 :(得分:1)
不,除非它是实际的单倍间距字体。
答案 6 :(得分:1)
我有时会为倒数做一件非常漂亮的事情:
HTML:
<div class="counter">
<span class="counter-digit counter-digit-0">2</span>
<span class="counter-digit counter-digit-1">4</span>
<span class="counter-digit counter-digit-divider">/</span>
<span class="counter-digit counter-digit-2">5</span>
<span class="counter-digit counter-digit-3">7</span>
</div>
SCSS:
$digit-width: 18px;
.counter {
text-align: center;
font-size: $digit-width;
position: relative;
width : $digit-width * 4.5;
margin: 0 auto;
height: 48px;
}
.counter-digit {
position: absolute;
top: 0;
width: $digit-width;
height: 48px;
line-height: 48px;
padding: 0 1px;
&:nth-child(1) { left: 0; text-align: right; }
&:nth-child(2) { left: $digit-width * 1; text-align: left;}
&:nth-child(3) { left: $digit-width * 2; text-align: center; width: $digit-width / 2} // the divider (/)
&:nth-child(4) { left: $digit-width * 2.5; text-align: right;}
&:nth-child(5) { left: $digit-width * 3.5; text-align: left;}
}
答案 7 :(得分:1)
我刚刚找到了text-transform: full-width;
实验关键字,该关键字:
[...]强制在正方形[...]内书写字符[...]
与否定的letter-spacing
结合使用,您可以获得不太可怕的结果:
<style>
pre {
font-family: sans-serif;
text-transform: full-width;
letter-spacing: -.2em;
}
</style>
<!-- Fixed-width sans-serif -->
<pre>
. i I 1 | This is gonna be awesome.
ASDFGHJK | This is gonna be awesome.
</pre>
<!-- Default font -->
. i I 1 | This is gonna be awesome.
<br>
ASDFGHJK | This is gonna be awesome.