Как узнать, когда применяется правило @ font-face - PullRequest
0 голосов
/ 30 ноября 2009

Есть ли способ узнать, когда применяется правило @ font-face? Я создаю правила @ font-face, которые используют data: URI из файла шрифта, запрошенного с синхронным запросом XMLHttpRequest в JavaScript, а затем сразу же пишем текст в элемент canvas, используя шрифт. Дело в том, что он фактически не использует шрифт при рисовании текста в течение первых нескольких миллисекунд. Мое текущее решение - блокировать выполнение на несколько миллисекунд, посылая синхронный запрос XMLHttpRequest, что является ужасным решением.

Я не могу сделать это асинхронным, поскольку он предназначен для реализации Обработки loadFont() функции, которая является синхронной, в Processing.js .

Я бы предпочел, чтобы решение не проверяло размеры символа, поскольку нет гарантии, что шрифт имеет определенный символ и что его размеры отличаются от того же символа текущего шрифта.

Ответы [ 2 ]

1 голос
/ 07 октября 2012

Краткий ответ: браузеры еще недостаточно хороши, чтобы позволить нам проверять наличие «загруженных и готовых к использованию» без фактического использования шрифта и его проверки.

Длинный ответ: Pjs поставляется со встроенным средством проверки шрифтов для предварительной загрузки шрифта (относится к https://github.com/pomax/font.js), но, как вы заметили, это не будет работать с правилами @ font-face, которые используют data-uri. A Обходной путь, который я бы предложил (хотя я еще не пробовал этого. Я просто предполагаю, что он будет работать на основе моей работы над Processing.js и загрузкой шрифтов в браузерах), заключается в использовании двух буферов PGraphic за пределами экрана. Сделайте их белыми фон с черной заливкой текста, сделайте текст ("X", 0,0) в первом буфере, а затем после загрузки шрифта используйте второй буфер для выполнения того же текста ("X", 0,0 "). Возьмите пиксель [] для каждого буфера и проведите параллельное сравнение:

boolean verifyFontLoad() {
  buffer1.loadPixels();
  buffer2.loadPixels();
  for (int i=0; i<buffer1.pixels.length; i++) {
    if (buffer1.pixels[i] != buffer2.pixels[i]) {
      return false; }}
  return true;
}

когда вы загружаете свой шрифт, где-то должно быть отслеживающее логическое значение, которое указывает состояние загрузки шрифта, устанавливается на «false» и после загрузки вашего шрифта в начале вызова draw () вызывается

void draw() {
  // code that does not rely on your font
  [...]

  // check state
  if(!fontLoaded) { fontLoaded = verifyFontLoaded(); }
  // not ready? "stop" drawing.
  if(!fontLoaded) { return; }
  // font ready. run code that relies on the font being ready
  else {
    // code that depends on your font being available goes here.
  }
}

Теперь, по крайней мере, вы можете избежать первых нескольких кадров, когда браузер завершил распаковку шрифта data-uri и загрузил его как ресурс @ font-face, но не успел передать его в систему рендеринга Canvas2D еще.

(стилизация элемента DOM на этом этапе с помощью шрифта на самом деле будет работать нормально, фактически его передают Canvas2D, что приводит к невозможности его использования одним или несколькими кадрами)

1 голос
/ 06 декабря 2010

Даже если вы не предпочитаете проверку размера, именно так работает функция Modernizr @ font-face и может быть лучшим способом:

Modernizr встраивает крошечный шрифт используя данные: URI. В этом единственном "" персонаж создан; тогда применяется к временному элементу которого innerHTML имеет значение «........» и ширина которого измеряется, сначала с основной шрифт с засечками, а затем с пользовательский шрифт применяется. Если ширина разные, мы знаем браузер представили новые данные шрифта мы Прилагаемые.

...