вызова
Как холст measureText
не в настоящее время поддерживая высоту измерения (восхождение + спуск), нам нужно сделать небольшой трюк DOM, чтобы получить высоту линии.
Поскольку фактическая высота шрифта или шрифта не обязательно (редко) соответствует шрифту размера, нам нужен более точный способ его измерения.
Решение
Fiddle demo
Результат будет выровнен по вертикали текст, который всегда соответствуют полотно шириной.
Это решение будет автоматически получить оптимальный размер для шрифта.
Первой функцией является обертывание measureText
для поддержки высоты. Если новая реализация метрик текста не доступна, то использовать DOM:
function textMetrics(ctx, txt) {
var tm = ctx.measureText(txt),
w = tm.width,
h, el; // height, div element
if (typeof tm.fontBoundingBoxAscent === "undefined") {
// create a div element and get height from that
el = document.createElement('div');
el.style.cssText = "position:fixed;font:" + ctx.font +
";padding:0;margin:0;left:-9999px;top:-9999px";
el.innerHTML = txt;
document.body.appendChild(el);
h = parseInt(getComputedStyle(el).getPropertyValue('height'), 10);
document.body.removeChild(el);
}
else {
// in the future ...
h = tm.fontBoundingBoxAscent + tm.fontBoundingBoxDescent;
}
return [w, h];
}
Теперь мы можем цикл, чтобы найти оптимальный размер (здесь не очень оптимизированы, но работает для этой цели - и я написал это только сейчас поэтому там могут быть ошибки, один из них, если текст - это всего лишь один символ, который не превышает ширину перед высотой).
Эта функция принимает минимум два аргумента, контекст и текст, другие необязательны, такие как имя шрифта (только имя), допуск [0,0, 1,0] (по умолчанию 0,02 или 2%) и стиль (то есть жирный, курсив и т.д.):
function getOptimalSize(ctx, txt, fontName, tolerance, tolerance, style) {
tolerance = (tolerance === undefined) ? 0.02 : tolerance;
fontName = (fontName === undefined) ? 'sans-serif' : fontName;
style = (style === undefined) ? '' : style + ' ';
var w = ctx.canvas.width,
h = ctx.canvas.height,
current = h,
i = 0,
max = 100,
tm,
wl = w - w * tolerance * 0.5,
wu = w + w * tolerance * 0.5,
hl = h - h * tolerance * 0.5,
hu = h + h * tolerance * 0.5;
for(; i < max; i++) {
ctx.font = style + current + 'px ' + fontName;
tm = textMetrics(ctx, txt);
if ((tm[0] >= wl && tm[0] <= wu)) {
return tm;
}
if (tm[1] > current) {
current *= (1 - tolerance);
} else {
current *= (1 + tolerance);
}
}
return [-1, -1];
}
Вы можете использовать measureText() См этот ответ http://stackoverflow.com/questions/10099226/determine-width-of-string-in-html5-canvas –
вас хотите оптимизировать размер шрифта в зависимости от размера вашего окна? Это то, о чем вы говорите? –
Да точно MESSIAH. Я хочу размер шрифта в холсте в соответствии с размером окна и длиной строки. –