Как уменьшить использование памяти Fabric.js при импорте файлов SVG с помощью clipPaths - PullRequest
0 голосов
/ 19 июня 2019

Я сталкиваюсь с ограничениями памяти WebKit с экземпляром Fabric.js при просмотре на мобильных устройствах и мог бы использовать некоторую помощь для определения наилучшего плана атаки.

Total canvas memory use exceeds the maximum limit (384 MB).

Моя страница импортирует файлы SVG, которые включают несколько объектов.Эти объекты сгруппированы, и группа имеет один clipPath.

Вот Пример SVG :

<svg id="Layer_1" data-name="Layer 1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="13.889in" height="9.722in" viewBox="0 0 1000 700">
  <defs>
    <clipPath id="clip-path">
      <circle cx="500" cy="350" r="327.5" style="fill: none"/>
    </clipPath>
  </defs>
  <g style="clip-path: url(#clip-path)">
    <circle cx="196.701" cy="90.183" r="29.908" style="fill: #0079d0"/>
    <circle cx="296.246" cy="99.166" r="21.743" style="fill: #0079d0"/>
    <circle cx="354.364" cy="108.67" r="22.485" style="fill: #0079d0"/>
...    

Однако при импорте SVG на холст через loadSVGFromURL, мой единственный clipPath, кажется, дублируется для каждого объекта в исходной группе, и для каждого из этих дубликатов clipPath создается новый элемент canvas.

// Create Fabric instance
canvasElement = document.getElementById('canvas');
canvas = this.__canvas = new fabric.Canvas('canvas', {
    enableRetinaScaling: true // default: true
});

// Load SVG image
fabric.loadSVGFromURL('https://dwpmcoaafgla7.cloudfront.net/objects.svg', function(objects, options) {

    // Group Objects
    var obj = fabric.util.groupSVGElements(objects, options);

    // Scale & Place
    var newSize = {
        width: Math.round(canvasElement.scrollWidth),
        height: Math.round((obj.height * canvasElement.scrollWidth) / obj.width)
    };
    var scale = newSize.width / obj.width;
    obj.set({
        scaleX: scale,
        scaleY: scale
    });
    canvas.add(obj);

}, null, { crossOrigin: 'anonymous' });

И они* * * * * * * * * * Скриншот вкладки 'canvas' веб-инспектора

Выполнение toSVG() показывает дубликаты clipPath, которые теперь присоединяются к каждому объектутоже:

<?xml version="1.0" encoding="UTF-8" standalone="no" ?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.1" width="1000" height="700" viewBox="0 0 1000 700" xml:space="preserve">
    <desc>Created with Fabric.js 3.1.0</desc>
    <defs></defs>
    <g transform="matrix(0.75 0 0 0.75 500 349.99)" style="">
        <g transform="matrix(1.33 0 0 1.33 -404.37 -346.41)" id="Layer_1" clip-path="url(#CLIPPATH_145)">
            <clipPath id="CLIPPATH_145">
                <circle transform="matrix(1 0 0 1 303.3 259.82)" id="clip-path" cx="0" cy="0" r="327.5"/>
            </clipPath>
            <circle style="stroke: none; stroke-width: 1; stroke-dasharray: none; stroke-linecap: butt; stroke-dashoffset: 0; stroke-linejoin: miter; stroke-miterlimit: 4; fill: rgb(0,121,208); fill-rule: nonzero; opacity: 1;" cx="0" cy="0" r="29.908"/>
        </g>
        <g transform="matrix(1.33 0 0 1.33 -271.65 -334.44)" id="Layer_1" clip-path="url(#CLIPPATH_146)">
            <clipPath id="CLIPPATH_146">
                <circle transform="matrix(1 0 0 1 203.75 250.83)" id="clip-path" cx="0" cy="0" r="327.5"/>
            </clipPath>
            <circle style="stroke: none; stroke-width: 1; stroke-dasharray: none; stroke-linecap: butt; stroke-dashoffset: 0; stroke-linejoin: miter; stroke-miterlimit: 4; fill: rgb(0,121,208); fill-rule: nonzero; opacity: 1;" cx="0" cy="0" r="21.743"/>
        </g>
        <g transform="matrix(1.33 0 0 1.33 -194.16 -321.77)" id="Layer_1" clip-path="url(#CLIPPATH_147)">
            <clipPath id="CLIPPATH_147">
                <circle transform="matrix(1 0 0 1 145.64 241.33)" id="clip-path" cx="0" cy="0" r="327.5"/>
            </clipPath>
            <circle style="stroke: none; stroke-width: 1; stroke-dasharray: none; stroke-linecap: butt; stroke-dashoffset: 0; stroke-linejoin: miter; stroke-miterlimit: 4; fill: rgb(0,121,208); fill-rule: nonzero; opacity: 1;" cx="0" cy="0" r="22.485"/>
        </g>
...

Нужны ли эти дубликаты, или я могу как-то их удалить?

Я понимаю, что могу отключить enableRetinaScaling, чтобы купить немного памяти на устройствах с сетчаткой / высоким разрешением,и / или изменить мое SVG-изображение, обрезав отдельные объекты вдоль обтравочной маски и полностью покончив с обтравочной маской , но я бы очень хотел исчерпать все другие варианты, прежде чем прибегать кк этому.

Вот CodePen

...