HTML5 canvas ctx.fillText не будет переносить строки? - PullRequest
92 голосов
/ 17 февраля 2011

Кажется, я не могу добавить текст на холст, если текст содержит "\ n".Я имею в виду, разрывы строк не отображаются / работают.

ctxPaint.fillText("s  ome \n \\n <br/> thing", x, y);

Приведенный выше код будет рисовать "s ome \n <br/> thing" на одной строке.

Это ограничение fillText или я делаю это неправильно?"\ n" есть и не печатаются, но они тоже не работают.

Ответы [ 16 ]

3 голосов
/ 30 мая 2012

Я думаю, что вы все еще можете положиться на CSS

ctx.measureText().height doesn’t exist.

К счастью, с помощью CSS hack-ardry (см. Typographic Metrics, чтобы узнать больше способов исправить более ранние реализации использования измерений CSS), мы можем найти высотутекст с помощью измерения offsetHeight a с такими же свойствами шрифта:

var d = document.createElement(”span”);
d.font = “20px arial”
d.textContent = “Hello world!”
var emHeight = d.offsetHeight;

от: http://www.html5rocks.com/en/tutorials/canvas/texteffects/

2 голосов
/ 05 сентября 2013

Я столкнулся с этим из-за той же проблемы.Я работаю с переменным размером шрифта, так что это учитывает это:

var texts=($(this).find('.noteContent').html()).split("<br>");
for (var k in texts) {
    ctx.fillText(texts[k], left, (top+((parseInt(ctx.font)+2)*k)));
}

, где .noteContent - contenteditable div, отредактированный пользователем (он вложен в jQuery каждой функции), и ctx.fontэто "14px Arial" (обратите внимание, что размер пикселя на первом месте)

2 голосов
/ 18 декабря 2010

Я не думаю, что это тоже невозможно, но обходной путь для этого - создать элемент <p> и расположить его с помощью Javascript.

0 голосов
/ 27 января 2019

Я сделал простой модуль npm для этого точного использования. https://www.npmjs.com/package/canvas-txt

Вы можете автоматически разбивать текст на несколько строк, а также на основе \n

0 голосов
/ 12 мая 2016

Мое решение ES5 для проблемы:

var wrap_text = (ctx, text, x, y, lineHeight, maxWidth, textAlign) => {
  if(!textAlign) textAlign = 'center'
  ctx.textAlign = textAlign
  var words = text.split(' ')
  var lines = []
  var sliceFrom = 0
  for(var i = 0; i < words.length; i++) {
    var chunk = words.slice(sliceFrom, i).join(' ')
    var last = i === words.length - 1
    var bigger = ctx.measureText(chunk).width > maxWidth
    if(bigger) {
      lines.push(words.slice(sliceFrom, i).join(' '))
      sliceFrom = i
    }
    if(last) {
      lines.push(words.slice(sliceFrom, words.length).join(' '))
      sliceFrom = i
    }
  }
  var offsetY = 0
  var offsetX = 0
  if(textAlign === 'center') offsetX = maxWidth / 2
  for(var i = 0; i < lines.length; i++) {
    ctx.fillText(lines[i], x + offsetX, y + offsetY)
    offsetY = offsetY + lineHeight
  }
}

Больше информации по этому вопросу - в моем блоге .

0 голосов
/ 03 ноября 2012

Элемент Canvas не поддерживает такие символы, как символ новой строки '\ n', вкладка '\ t' или тег
.

Попробуйте:

var newrow = mheight + 30;
ctx.fillStyle = "rgb(0, 0, 0)";
ctx.font = "bold 24px 'Verdana'";
ctx.textAlign = "center";
ctx.fillText("Game Over", mwidth, mheight); //first line
ctx.fillText("play again", mwidth, newrow); //second line 

или возможнонесколько строк:

var textArray = new Array('line2', 'line3', 'line4', 'line5');
var rows = 98;
ctx.fillStyle = "rgb(0, 0, 0)";
ctx.font = "bold 24px 'Verdana'";
ctx.textAlign = "center";
ctx.fillText("Game Over", mwidth, mheight); //first line

for(var i=0; i < textArray.length; ++i) {
rows += 30;
ctx.fillText(textArray[i], mwidth, rows); 
}  
...