Выполнение HTML -> преобразование Canvas без блокировки интерфейса - PullRequest
0 голосов
/ 06 января 2019

Мне нужно преобразовать HTML внутри iframe в png и отправить его на сервер после сохранения нового шаблона в GrapesJS редакторе веб-шаблонов. Проект в Angular.

После попытки использовать несколько библиотек (html2canvas, html-to-image, ...), но большинство из них имели ужасное качество преобразования (т. Е. CSS не применялись на холсте должным образом)

Итак, я решил согласиться с rasterizeHtml, который надежно отображает элементы, но значительно медленнее (approx 5s-8s per render). Во время этого процесса происходит много запросов ресурсов (занимает немного меньше времени, чем весь процесс), цель которых я не совсем понимаю, но это может быть большой частью медлительности, поскольку они занимают довольно много секунд.

enter image description here

Пока библиотека выполняет свою функцию, поток пользовательского интерфейса заблокирован и, следовательно, не отвечает. Анимации, которые должны происходить, не происходят, пользователь не может взаимодействовать со страницей и т. Д.

Я думал о переносе процесса в веб-работника, но поскольку веб-работник не может получить доступ к объектам окна / документа, это не из окна (каламбур предназначен).

Есть ли другой способ, которым я мог бы выполнить преобразование неблокирующим способом? Или, по крайней мере, заставить интерфейс обновляться, чтобы анимации отображались правильно? Возможно, я делаю что-то неэффективное?

updatePreviewThumbnail() {
  const iframe = document.getElementsByTagName('iframe')[0];
  const body = iframe.contentDocument.getElementsByTagName('html')[0];
  const el = iframe.contentDocument.getElementById('wrapper').children[0];
  const size = el.getBoundingClientRect();

  const canvas: any = document.createElement('CANVAS');
  canvas.width = size.width;
  canvas.height = size.height;
  let isConverted = false;
  rasterizeHTML.drawHTML(body.innerHTML, canvas).then(() => {
    isConverted = true;

    let file: File;

    canvas.toBlob((blob) => {
      file = new File([blob], 'screenshot.png', {type: 'image/png'});
      this.editorService.uploadFileToAmazon(file).subscribe(() => noop());
    }, 'image/png', 1);
...
  });
}

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

...