CSS字体大小(响应式),相对于设备分辨率?
Posted
技术标签:
【中文标题】CSS字体大小(响应式),相对于设备分辨率?【英文标题】:CSS Font size (responsive), relative to device resolution? 【发布时间】:2017-04-25 00:47:15 【问题描述】:假设我们有以下test.htm
:
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<style type="text/css">
.testdiv, .testdivB, .testdivC
width: 50%;
height: 30%;
margin: 6px;
border: 2px solid gray;
font-size: 4em;
.testdivB
font-size: 12px;
.testdivC
font-size: 30pt;
</style>
</head>
<body>
<div class="testdiv">Test one writing</div>
<div class="testdivB">Test another writing</div>
<div class="testdivC">Test three writing</div>
</body>
</html>
我尝试在 Chromium 中使用开发者工具对此进行测试,该工具允许我模拟不同的设备;这里:
* Apple iPhone 4 : device resolution 320 x 480 , a/r 0.666667
* Google Nexus 10 : device resolution 800 x 1280 , a/r 0.625
* Amazon Kindle Fire HDX: device resolution 1600 x 2560 , a/r 0.625
结果是这样的:
在此示例中,所有设备都是纵向的,并且具有“几乎”相同的纵横比 (~ 0.6+),即使它们的分辨率差异很大。
因此,在前两种情况下,相对于设备屏幕大小,我得到的字体大小大致相同,这是我想要实现的(尽管我很困惑testdivB
也显示几乎相同的大小,但它应该更小) - 这一切都很好。
但是,在第三个示例中,在具有最大分辨率的设备上,testdivB
(在px
中定义)相对于设备屏幕尺寸要小得多。 testdivA
也不足为奇,因为em
是相对于浏览器的“计算字体大小”而言的——如果我没记错的话,它也以像素表示。
但是,我认为pt
会考虑设备屏幕分辨率,但它似乎没有:
http://www.w3.org/Style/Examples/007/units.en.html
过去,CSS 要求实现即使在计算机屏幕上也能正确显示绝对单位。但由于错误实现的数量超过了正确实现的数量,而且情况似乎没有改善,CSS 在 2011 年放弃了这一要求。目前,绝对单位必须仅在打印输出和高分辨率设备上正确工作。
好的,那么我有哪些选项可以在所有三种情况下实现大致相同的字体大小(相对于设备屏幕大小):
如果我不想使用 javascript(仅 HTML + CSS)? 如果我确实想使用 JavaScript(我猜有一种方法可以查询设备屏幕 - 而不是视口 - 分辨率,但我不确定是否真的有)?【问题讨论】:
我相信媒体查询可以在这里与 Roberrrt 的答案一起使用,并使用类而不是 ID,并根据 Roberrrt 的代码使用相同的类名但大小不同,所以你最终会得到类似 @987654335 的东西@ 在不同的媒体查询和font-size: calc(Xem + Xvmin);
类型的事物中。不过,这只是我的 “2 美分”。
我很好奇,我的一个解决方案真的有帮助/有效吗:)?
确实,@Teepeemm,应该是.testdivC
- 我更正了,但现在我不确定截图是用错误的.testdivB
还是正确的.testdivC
(但看起来它是用正确的)
嗨@Roberrrt,你的回答我已经posted a comment,但它似乎在那里迷路了;我现在还有基于 JavaScript 的posted my own answer,它应该更详细地解释我在寻找什么;简而言之,我的问题是vmin
是用视口表示的,而不是设备分辨率,如果在桌面上使用并且浏览器不是“全屏”,这可能会给出错误的结果。
【参考方案1】:
不久前,我写了一个关于如何使用纯 HTML/CSS 实现此目的的小教程/示例:
响应单元 (vmin
/vmax
)
#small
font-size: calc(1em + 1vmin);
#medium
font-size: calc(1em + 2vmin);
#large
font-size: calc(1em + 3vmin);
<div id="small">Small text</div>
<div id="medium">Medium text</div>
<div id="large">Large text</div>
规则vmin
在您的上下文中非常有用。它需要 vmin: 屏幕最小边的 1/100。不管方向。将它与 calc()
中的基本 1em 结合起来,为我们提供了一种在 font-size
上应用小型自定义响应方面的好方法。
替代方法 (vw
/vh
)
#small
font-size: calc(1em + 1vw);
#medium
font-size: calc(1em + 2vw);
#large
font-size: calc(1em + 3vw);
<div id="small">Small text</div>
<div id="medium">Medium text</div>
<div id="large">Large text</div>
如果您希望对实际纵横比进行更多控制,我建议您使用vw
而不是vmin
。视口宽度 (vw) 占视口宽度的 1/100。
基于视口纵横比的响应单元(vmin
和 vmax
):
#test1
font-size: calc((.4em + 1vmin) + (.4em + 1vmax));
#test2
font-size: calc((.4em + 2vmin) + (.4em + 2vmax));
#test3
font-size: calc((.4em + 3vmin) + (.4em + 3vmax));
<div id="test1">Small text</div>
<div id="test2">Medium text</div>
<div id="test3">Large text</div>
我对这个解决方案非常满意,这种方式允许我们同时考虑视口宽度和长度。我们将基本字体大小一分为二(在本例中为 .4em),然后将其乘以 1vmin 和 1vmax,然后将这两个值相加来确定字体大小。
【讨论】:
巧合的是,前段时间我也浏览了几篇关于同一主题的文章。只是在这里大声思考;如果使用一个类,然后根据屏幕大小将其应用于媒体查询,这不是也有意义吗?由于 id 是唯一的。 对不起,我不能提供一个小提琴,但我很确定你知道我的意思 ;-) 最后,我最终使用了不同字体大小的媒体查询。 @Roberrrt 但我肯定会尝试你的方法:-) 结合起来会很有意义,让我总结一下自己的网站来测试一些东西。 @Fred-ii- 我通常选择 20em/40em/80em 媒体查询断点,并在其上“增强”基本字体大小,calc(1em + 1vw)。 calc(1.2em + 1vw)。calc(1.5em + 1vw)
.
我认为您可以将(.4em + 1vmin) + (.4em + 1vmax)
更改为(.8em + 1vw + 1vh)
。令我惊讶的是,没有一种方便的方式可以说“使其成为正常尺寸”并在所有设备上都可读。【参考方案2】:
好的,我想我找到了一个我可以使用的解决方案,它使用 JavaScript。使用下面粘贴的代码,我现在在 Chromium 开发人员工具中在不同设备上进行测试时得到了这个:
正如所见,第一个 div 的相对大小 .testdiv
与 em
的规范现在跨设备大小保留(这是我想要的); px
在第二个 div 中,正如预期的那样不会保留相对大小——pt
规范的第三种情况也没有。
我遇到的第一个问题是如何获得设备分辨率。请注意,vw
、vh
- 以及 vmin
和 vmax
- 与 viewport 大小相关,即窗口大小。这在移动设备中不是什么大问题,因为移动设备上的浏览器通常以“全屏”启动(我什至不确定是否可以在移动设备、ios 或 android 上调整浏览器/应用程序窗口的大小) - 但它可能如果在桌面上使用浏览器会出现问题,因为浏览器最终可能无法全屏显示。
谢天谢地,可以使用 JavaScript (How to detect the screen resolution with JavaScript?) 获得设备分辨率,在这种情况下,我可以得到设备的宽度和高度(以像素为单位) - 并从中计算出 devicemin
是两者中较小的一个(类似于vmin
)。然后我将<html>
元素的“基本字体大小”设置为devicemin
(这是我自己的任意选择)的2.67%(以像素为单位)。希望这样可以确保我在不同分辨率的设备上具有相同的字体大小(相对于设备分辨率)。
第二个问题,有点出乎我的意料,是你必须在头脑中有一个<meta name="viewport" content="width=device-width, initial-scale=1.0"/>
条目/指令!否则,没有它,iOS 浏览器只会应用他们自己的字体大小/缩放,因此我们会得到一个意想不到的结果:
事实上,我对 Chromium 开发者工具中的这个结果感到非常惊讶,以至于我不得不在 Xcode iOS 模拟器中尝试测试 - 令人惊讶的是,Chromium 开发者工具实际上确实模拟了与 iOS 模拟器相同的行为做了(左图是开发者工具中的代码,右图是iOS模拟器中的OP代码)。有关这方面的更多信息,请参阅Some font-size's rendered larger on Safari (iPhone) ...
无论如何,既然我有这样的“基本”字体大小,我可以根据宽度
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<meta name="viewport" content="width=device-width, initial-scale=1.0"/> <!-- MUST have, so iPhone doesn't autozoom and change the fontsize! -->
<script type="text/javascript">
// https://***.com/questions/2242086/how-to-detect-the-screen-resolution-with-javascript
var devicewidth = window.screen.width;
var deviceheight = window.screen.height;
var devicemin = Math.min(devicewidth, deviceheight);
// say we want base font size: 16px @ 600px (min of 800x600); 16/600 = 0.0266667
var basefontsize = Math.round(0.0267*devicemin);
// apply:
var rootElement = document.documentElement;
rootElement.style.fontSize = basefontsize;
// report:
console.log(navigator.userAgent);
var report = "device res: " + devicewidth + " x " + deviceheight + " ; base font size: " + basefontsize + "/" + rootElement.style.fontSize;
console.log(report);
function reporter()
document.getElementById("dreport").innerHTML = report + "/" + document.documentElement.style.fontSize + " ... " + navigator.userAgent;
window.onload = reporter;
</script>
<style type="text/css">
body
/* https://***.com/questions/3226001 ; no real need/effect in this case, though */
-webkit-text-size-adjust: none;
.testdiv, .testdivB, .testdivC
width: 50%;
height: 30%;
margin: 6px;
border: 2px solid gray;
font-size: 4em;
.testdivB
font-size: 12px;
.testdivC
font-size: 30pt;
#dreport
font-size: 0.76em;
</style>
</head>
<body>
<div id="dreport"></div>
<div class="testdiv">Test one writing</div>
<div class="testdivB">Test another writing</div>
<div class="testdivC">Test three writing</div>
</body>
</html>
【讨论】:
对问题的出色描述和解释,包括解决问题的绝妙方法。做得很好!【参考方案3】:另外,您可以使用%
符号。如下所示:
div.wrapper
font-size: 28px;
div.small
font-size: 80%;
div.big
font-size: 150%;
<div class="wrapper">
<div class="small">Small text</div>
<div class="normal">Normal text</div>
<div class="big">Big text</div>
</div>
【讨论】:
谢谢@nmnsud - 但据我所知,% 是相对于父字体大小的,最终根有一个“计算字体大小”再次以像素为单位指定,所以我再次期望(这就是我在 Chromium 开发人员工具中得到的)Kindle HDX 上的字体比其他两种情况更小(相对于设备大小);有什么办法解决吗? 谢谢@nmnsud - 但我想我不清楚;我的意思是,即使您将像素数量指定为起始字体大小,比如 28 像素,它与 Nexus 10 (28/800) 的屏幕宽度的比率总是比相同的比率小得多具有较大分辨率的设备,例如 Kindle HDX (28/1600),因此您在该设备上具有较小的相对字体大小,并且此后将在所有相对单位中传播(%,em,rem ...)可以修复这个,如果可以查询 device 屏幕大小,但是 vw, vh 只查询视口大小。以上是关于CSS字体大小(响应式),相对于设备分辨率?的主要内容,如果未能解决你的问题,请参考以下文章