Подтвердить что ты не робот

SVG: почему внешний css переопределяет встроенный стиль для текста?

Я играю с использованием SVG gradientFill, чтобы визуально "обрезать" длинные текстовые строки в диаграмме d3.js.

Кажется, что внешний стиль CSS для заполнения будет переопределять встроенный стиль заливки градиента в SVG... это всегда так? Как я могу применить эту заливку градиента?

В этом тестовом случае я определил линейный градиент в svg defs, а затем применил заливку градиента к двум группам текста. http://jsfiddle.net/rolfsf/uX2kH/3/

var labelColWidth = 200;
var svg =  d3.select('#test').append('svg')
            .attr('width', 500)
            .attr('height', 500);

var defs = svg.append('svg:defs');

var textgradient = defs.append('svg:linearGradient')
            .attr('gradientUnits', 'userSpaceOnUse')
            .attr('x1', 0).attr('y1', 0).attr('x2', 40).attr('y2', 0)
            .attr('id', 'theGradient')
            .attr('gradientTransform',  'translate(' + (labelColWidth - 40) + ')');

    textgradient.append('svg:stop').attr('offset', '0%').attr('style', 'stop-color:rgb(0,0,0);stop-opacity:1')
    textgradient.append('svg:stop').attr('offset', '100%').attr('style', 'stop-color:rgb(0,0,0);stop-opacity:0');


var data = [[0, "xyzzy xyzzy"], [1, "xyzzy xyzzy xyzzy xyzzy xyzzy"], [2, "xyzzy xyzzy xyzzy xyzzy xyzzy xyzzy"], [3, "xyzzy xyzzy xyzzy"], [4, "xyzzy xyzzy"], [5, "xyzzy xyzzy xyzzy xyzzy xyzzy xyzzy xyzzy xyzzy xyzzy xyzzy"]];

var testGroup = svg.append('g')
    .attr('transform',  'translate(50, 100)');

var testGroup2 = svg.append('g')
    .attr('transform',  'translate(50, 250)')
    .attr('class', 'group2');

testGroup.selectAll('text').data(data)
  .enter().append('svg:text')
  .attr('fill', 'url(#theGradient)')
  .attr('x', 0)
  .attr('y', function(d, i) { return (i+1) * 20; })
  .text(function(d, i) { return d[1]; });

testGroup2.selectAll('text').data(data)
  .enter().append('svg:text')
  .attr('fill', 'url(#theGradient)')
  .attr('x', 0)
  .attr('y', function(d, i) { return (i+1) * 20; })
  .text(function(d, i) { return d[1]; });

то в CSS я определяю заполнение для текста .group2

.group2 text {
    fill: #000;
}

первая группа имеет градиентную заливку, вторая - нет.

Не следует ли иметь встроенный стиль?

Спасибо!

4b9b3361

Ответ 1

Так как в SVG, как и HTML перед ним, стилирование стиля trump стилей.

fill="red" ниже НЕ является "встроенным стилем", style="fill:green" является встроенным стилем.

<svg width="400" height="400">
  <text x="50" y="50" fill="red" style="fill:green">This will be green</text>
</svg>

Ответ 2

Из спецификация SVG

Для пользовательских агентов, которые поддерживают CSS, атрибуты презентации должны быть переведены в соответствующие правила стиля CSS в соответствии с правилами, описанными в Приоритете презентаций, не относящихся к CSS ([CSS2], раздел 6.4.4), с дополнительным разъяснением того, что атрибуты презентации концептуально вставляются в новую таблицу стилей автора, которая является первой в коллекции стилей стилей автора. Атрибуты представления, таким образом, будут участвовать в каскаде CSS2, как если бы они были заменены соответствующими правилами стиля CSS, размещенными в начале таблицы стилей автора со спецификой нуля. В общем, это означает, что атрибуты презентации имеют более низкий приоритет, чем другие правила стиля CSS, указанные в стилях стилей автора или атрибутах стиля.

Таким образом, вы можете использовать встроенный стиль, а не атрибут представления, например.

.attr('style', 'fill : url(#theGradient)')

Ответ 3

В моем случае это было так же просто, как заменить attr на style в цепочке d3:

.style('stroke', 'url(#gradient--min)')