我很难理解字体缩放。

我目前有一个字体大小为100%的网站。但这是100%的吗?这似乎是在16个像素处计算出来的。

我的印象是,100%会以某种方式指代浏览器窗口的大小,但显然不是因为无论窗口大小调整为移动宽度还是宽屏桌面,都是16像素。

如何使站点上的文本与其容器相关?我尝试过使用它们,但这也无法扩展。

我的理由是,当你调整大小时,像我的菜单这样的东西会变得压扁,所以我需要减少.menuItem等元素相对于容器宽度的px字体大小。(例如,在大型桌面上的菜单中,22px的效果非常好。向下移动到平板电脑宽度,16px更合适。)

我知道我可以添加断点,但我真的希望文本能够缩放并具有额外的断点,否则,我将以每100像素宽度减少数百个断点来控制文本。


当前回答

我自己的解决方案,基于jQuery,通过逐渐增加字体大小来工作,直到容器的高度大大增加(这意味着它有换行符)。

它很简单,但工作得很好,而且非常容易使用。您不必了解所使用的字体,一切都由浏览器处理。

你可以在上面玩http://jsfiddle.net/tubededentifrice/u5y15d0L/2/

神奇就发生在这里:

var setMaxTextSize=function(jElement) {
    // Get and set the font size into data for reuse upon resize
    var fontSize=parseInt(jElement.data(quickFitFontSizeData)) || parseInt(jElement.css("font-size"));
    jElement.data(quickFitFontSizeData, fontSize);

    // Gradually increase font size until the element gets a big increase in height (i.e. line break)
    var i = 0;
    var previousHeight;
    do
    {
        previousHeight=jElement.height();
        jElement.css("font-size", "" + (++fontSize) + "px");
    }
    while(i++ < 300 && jElement.height()-previousHeight < fontSize/2)

    // Finally, go back before the increase in height and set the element as resized by adding quickFitSetClass
    fontSize -= 1;
    jElement.addClass(quickFitSetClass).css("font-size", "" + fontSize + "px");

    return fontSize;
};

其他回答

功能如下:

document.body.setScaledFont = function(f) {
  var s = this.offsetWidth, fs = s * f;
  this.style.fontSize = fs + '%';
  return this
};

然后将所有文档子元素的字体大小转换为em或%。

然后向代码中添加类似的内容以设置基本字体大小。

document.body.setScaledFont(0.35);
window.onresize = function() {
    document.body.setScaledFont(0.35);
}

http://jsfiddle.net/0tpvccjt/

这个呢?将父级的字体大小设置为等于其宽度,然后使用文本元素字体大小的百分比。

.element {
    width: 400px;
    font-size: 400px; /* equal to width */
}

.text {
    width: 10%;  /* will be 40px */
}

我发现这非常简单,特别是当你处理图标时,但也适用于文本。

/*造型的开始*/* {边距:0;填充:0;框大小调整:边框框;}.box格式{显示:块;背景:矢车菊蓝;高度:最大含量;边距底部:32px;}/*样式结束*/.方框p{字体大小:20%;}<div class=“box”style=“width:400px;font-size:400px”><p>文本</p></div><div class=“box”style=“width:128px;font-size:128px”><p>文本</p></div><div class=“box”style=“width:10vw;font-size:10vw”><p>文本</p></div><div class=“box”style=“width:64px;font-size:64px”><p>文本</p></div>

我想喜欢接受的答案,但从根本上说,符合我的标准的答案都需要使用图书馆。我决定编写一个非常适合我的简单函数,而不是让自己熟悉另一个库,然后找出如何使用它并准备在它不工作时进行调试。

理论:

传入需要匹配的字符串传入要从中继承文本样式的父级可选地传入自定义属性(例如,您将从中继承字体和其他属性的类/id,或者仅传入自定义内联样式)函数将在屏幕外创建一个文本元素,其中包含该文本、该父元素和这些属性,字体大小为1px,并对其进行测量然后,在循环中,它将逐像素增加字体大小,直到超过宽度限制;一旦完成,它将返回最后一个合适的然后删除测试元素当然,这一切都发生在眨眼之间

限制:

我不在乎动态调整屏幕大小,因为这与我的上下文无关。在生成文本时,我只关心运行时的屏幕大小。我依赖一个小助手函数,我也在代码的其他地方使用它,它基本上作为mithril.js的单函数版本存在;老实说,我几乎在每个项目中都使用这个小功能,它值得自己学习。

  function findMaxFontSize(
    string="a string", 
    parent=document.body, 
    attributes={id:'font-size-finder',class:'some-class-with-font'}
  ) {
    // by using parent, we can infer the same font inheritance;
    // you can also manually specify fonts or relevant classes/id with attributes if preferred/needed
    attributes.style = 'position:absolute; left:-10000; font-size:1px;' + (attributes.style || "");
    let testFontEl = createEl('p', attributes, string);
    parent.appendChild(testFontEl);
    let currentWidth = testFontEl.offsetWidth;
    let workingFontSize = 1;
    let i = 0;
    while (currentWidth < maxWidth && i < 1000) {
      testFontEl.style.fontSize = Number(testFontEl.style.fontSize.split("px")[0]) + 1 + "px";
      currentWidth = testFontEl.offsetWidth;
      if (currentWidth < maxWidth) {
        workingFontSize = testFontEl.style.fontSize;
      }
      i++; // safety to prevent infinite loops
    }
    console.log("determined maximum font size:",workingFontSize,'one larger would produce',currentWidth,'max width allowed is',maxWidth,'parent is',parent);
    parent.removeChild(testFontEl);
    return workingFontSize.split("px")[0];
  }
// utility function, though you could easily modify the function above to work without this.
  // normally these have no default values specified, but adding them here
  // to make usage clearer.
  function createEl(tag="div", attrs={class:'some-class'}, children=[]) {
    let el = document.createElement(tag);
    if (attrs) {
      Object.keys(attrs).forEach(attr => {
        el.setAttribute(attr, attrs[attr])
      })
    }
    if (children) {
      children = Array.isArray(children) ? children : [children];
      for (let child of children) {
        if (typeof child === "number") child = ""+child;
        if (typeof child === "string") {
          el.insertAdjacentText("afterbegin", child);
        }
        else {
          try {
            el.appendChild(child)
          } catch (e) {
            debugger
          }
        }
      }
    }
    return el;
  };

use:

    const getUsername = () => "MrHarry";
    const username = getUsername();
    const anchor = document.querySelector('.container');
    const titleFontSize = findMaxFontSize(`Welcome, ${username}`, anchor, {style:'font-weight:900;'});
    const titleFontStyle = `font-size:${titleFontSize}px;`;  

为了使字体大小适合其容器,而不是窗口,请参阅我在这个问题中分享的resizeFont()函数(其他答案的组合,其中大多数已经链接到这里)。它使用window.addEventListener('size',resizeFont);触发;。

Vanilla JavaScript:调整字体大小以适应容器

JavaScript:

function resizeFont() {
  var elements  = document.getElementsByClassName('resize');
  console.log(elements);
  if (elements.length < 0) {
    return;
  }
  _len = elements.length;
  for (_i = 0; _i < _len; _i++) {
    var el = elements[_i];
    el.style.fontSize = "100%";
    for (var size = 100; el.scrollHeight > el.clientHeight; size -= 10) {
      el.style.fontSize = size + '%';
    }
  }
}

您可能可以使用vw/vh作为备用,因此您可以使用JavaScript动态分配em或rem单位,确保在禁用JavaScript时字体可以缩放到窗口。

将.resize类应用于包含要缩放的文本的所有元素。

在添加窗口调整大小事件侦听器之前触发函数。然后,当加载页面以及调整页面大小时,任何不适合其容器的文本都将被缩小。

注意:默认字体大小必须设置为em、rem或%,以获得正确的结果。

在艺术上,如果您需要在相同的宽度内放置两行或多行文本,而不管它们的字符数如何,那么您有很好的选择。

最好找到一个动态解决方案,这样无论输入什么文本,我们都会得到一个很好的显示。

让我们看看我们可以如何接近。

var els=document.querySelectorAll(“.divtext”),refWidth=els[0].clientWidth,refFontSize=parseFloat(window.getComputedStyle(els[0],null).getPropertyValue(“字号”);els.forEach((el,i)=>el.style.fontSize=refFontSize*refWidth/els[i].clientWidth+“px”)#集装箱{显示:内联块;背景色:黑色;衬垫:0.6vw 1.2vw;}.div文本{显示:表格;颜色:白色;字体系列:影响;字体大小:4.5vw;}<div id=“container”><div class=“divtext”>这只是一个</div><div class=“divtext”>示例</div><div class=“divtext”>向您展示</div><div class=“divtext”>您想要</div></div>

我们所做的只是获取第一行的宽度(els[0].clientWidth)和字体大小(parseFloat(window.getComputedStyle(els[0],null).getPropertyValue(“字体大小”))作为引用,然后计算后续行的字体大小。