Асинхронно загруженный SVG-фильтр feColorMatrix работает в Chrome, а не в Safari или Firefox

Я загружаю SVG-фильтр асинхронно в зависимости от даты и времени пользователя. Он отлично работает в Chrome, но не в Safari/Firefox.

Сокращенный пример

1. HTML:
Нажав на кнопку, мы загрузим svg-строку в загрузчик DIV#svg:

<img src="http://beta.zonabern.ch/project/uploads/img0136-640x480.jpg" alt="" />

<div id="svg-loader"></div>
<button id="loader">Load</button>

2. CSS: свойство filter-поддерживается префиксом vendor-prefix

img {
  filter: url("#monochrome");
  -webkit-filter: url("#monochrome");
}

3. Javascript / JQuery : нажимая на кнопку, я имитирую асинхронную загрузку svg-данных.

$(function() {
    $( '#loader' ).on( 'click', function() {
        $( '#svg-loader' ).empty().html('<svg class="defs-only"><filter id="monochrome" color-interpolation-filters="sRGB" x="0" y="0" height="100%" width="100%"><feColorMatrix type="matrix" in="SourceGraphic" values="0.33984375 0 0 0 0.66015625 0.4140625 0 0 0 0.5859375 0.3203125 0 0 0 0.6796875 0 0 0 1 0"/></filter></svg>');
    });
});

Для лучшей читаемости, снова svg:

<svg class="defs-only">
    <filter id="monochrome" 
            color-interpolation-filters="sRGB" 
            x="0" 
            y="0" 
            height="100%" 
            width="100%">
        <feColorMatrix type="matrix" in="SourceGraphic"
                       values="0.33984375 0 0 0 0.66015625
                               0.4140625  0 0 0 0.5859375
                               0.3203125  0 0 0 0.6796875
                               0          0 0 1 0" />
    </filter>
</svg>

Этот фильтр должен превратить изображение выше в фиолетово-белое изображение.

Смотрите пример Codepen здесь, работающий в Chrome, но не в Safari/Firefox.

1 ответ

  1. Я думаю, что самое простое решение-назначить свои filterправила CSS классу:

    .filtered {
      filter: url("#monochrome");
      -webkit-filter: url("#monochrome");
    }
    

    Затем назначьте этот класс <img>только после загрузки SVG.

    $( '#loader' ).on( 'click', function() {
      $( '#svg-loader' ).empty().html('<svg>...</svg>');
      $("#myimg").addClass("filtered");
    });
    

    Обновленный codepen здесь. Это работает на FF. Я не могу тестировать Safari, потому что я на компьютере.