在HTML画布上格式化文本
Formatting text on HTML canvas
我正在使用HTML Canvas和香草javascript制作一个游戏。我是javascript的新手,所以这可能比我想象的要容易。我有两个表示卡片的对象数组,每个对象都有一个40-100个字符的"文本"属性,动态绘制在屏幕上的一张130 x 70像素的卡片上。
我需要格式化文本以适应卡片的宽度限制(130px),并在必要时创建新行。
感谢提供的任何帮助
经过编辑以使其更加清晰
您可以使用画布API中的measureText()
方法
正如Ken Fyrstenberg在这个令人敬畏的答案中所指出的,
画布'
measureText
当前不支持测量高度(上升+下降)。
下面的尝试使用一个硬编码的 Ken的答案确实提供了一种通过编程找到它的方法lineHeight
值,您必须在呈现文本之前找到该值
[编辑:由于markE在下面的评论,它现在使用的字体大小近似为1.286*。]
所以,它是肮脏的,必须有更好的方法来做到这一点,但无论如何。。。
var input = document.querySelector('input');
input.addEventListener('keyup', write, false);
var c = document.createElement('canvas'),ctx = c.getContext('2d');
c.width = 400, c.height = 150; document.body.appendChild(c);
// simple box object for the card
var card = {x: 25, y: 25, w: 130, h: 70};
ctx.fillStyle = "#CCCCCC";
ctx.fillRect(card.x, card.y, card.w, card.h);
var fontSize = 12;
ctx.font=fontSize+'px arial';
// Margins multipliers are chosen arbitrarly here, just because they fit well to my eyes
var margins = {t: 1.25*fontSize, l: .7*fontSize, b: 2*fontSize, r: .7*fontSize},
marginsX = margins.l+margins.r,
marginsY = margins.t+margins.b;
// As suggested by markE, lineHeight is set to 1.286* the fontSize,
// for a calculated way, see Ken's answer here : https://stackoverflow.com/a/17631567/3702797
var lineHeight = 1.286*fontSize;
// just a shortcut
var lineWidth = function(text) {
return ctx.measureText(text).width;
};
function write() {
var txt = this.value;
// Redraw our card
ctx.fillStyle = "#CCCCCC";
ctx.fillRect(card.x, card.y, card.w, card.h);
// Split the input at any white space, you might want to change it
var txtLines = txt.split(/'s/);
var i = 0, maxWidth = card.w - marginsX;
if(lineWidth(txt[0])>card.w || lineHeight>card.h-(margins.t/4) ){
console.warn('TOO BIG FONT!!');
return;
}
while(txtLines[i]) {
// If our current line merged with the next line width isn't greater than the card one
if (txtLines[i+1] && lineWidth(txtLines[i] + ' ' + txtLines[i+1]) < maxWidth) {
// Merge them
txtLines[i] += ' ' + txtLines.splice(i + 1, 1);
}
else {
// Is the one word too big? --> Dirtyphenation !
if (lineWidth(txtLines[i]) > maxWidth) {
// Add a new index with the two last chars since we'll add a dash
txtLines.splice(i+1, 0, "");
// If it's still too big
while (lineWidth(txtLines[i]) > maxWidth) {
var lastChars = txtLines[i].length - 2;
// Append those two last chars to our new array index
txtLines[i+1] = txtLines[i].substring(lastChars) + txtLines[i+1];
// Remove them from our current index
txtLines[i] = txtLines[i].substring(0, lastChars);
}
// Add the final dash
txtLines[i] += "-";
}
// Is our text taller than the card height?
if (lineHeight*i > card.h-marginsY){
// If there is more text coming after...
if (txtLines[i+1]){
// ...and it fits in the line
if(lineWidth(txtLines[i]+' '+txtLines[i+1])<maxWidth){
continue;
}
// ...and it doesn't fit in the line
else{
// Does a single char fit with the ellipsis ?
if(lineWidth(txtLines[i][0]+'...')<maxWidth){
// remove a char until we can put our ellipsis
while (lineWidth(txtLines[i]+'...') > maxWidth){
txtLines[i] = txtLines[i].substring(0,txtLines[i].length-1)
}
}else{
return;
}
txtLines[i] += '...';
// remove the surplus from the array
txtLines = txtLines.slice(0,i+1);
}
}
// stop looping here since we don't have space anymore
break;
}
// Go to next line
i++;
}
}
ctx.fillStyle = "#000";
// Where to draw
var x = card.x + (margins.l);
var y = card.y + (margins.t);
// Iterate through our lines
for (var i = 0; i < txtLines.length; i++) {
ctx.fillText(txtLines[i], x, y + (i * lineHeight));
}
}
canvas {border: 1px solid}
<input type="text" />
相关文章:
- 在HTML画布上格式化文本
- 如果所选内容在标记内,如何获取格式化文本
- 使用数字OnfocusOut/OnBlur格式化文本框
- 我想阅读一个格式化文本的html标签.使用javascript
- 使用 javascript 更改预先格式化文本中的值
- 用于格式化文本的 JavaScript 函数
- 如何使用 Javascript 从字符串中间提取然后重新格式化文本
- 带有跨浏览器换行符的 Javascript 预格式化文本
- 使用 jquery 格式化文本文件
- JSON 是否存储格式化文本并保持格式
- 使用格式化文本获取 DIV 或跨度的动态宽度高度
- 使用 html() 或 text() 方法返回格式化文本
- 通过 Javascript 在 Photoshop CS6+ 中格式化文本
- 如何将格式化文本从数据库返回到TinyMCE
- 仅显示mysql数据库中的格式化文本
- 将tinymce中的格式化文本存储在数据库中
- 在CSS弹出框中格式化文本的问题
- 在文本字段中键入文本时格式化文本
- 解析格式化文本并按顺序提取值
- 使用Javascript或jQuery自定义标记来格式化文本