如何将CSS样式展平为svg图形

时间:2016-11-03 11:36:26

标签: javascript css d3.js svg

我正在尝试将svg图转换为png图像。为此,我首先使用库'canvg'将我的svg图转换为画布,然后使用方法canvas.toDataURL('image/png')最终将我的图转换为png图像。我使用库'canvg'的原因是因为我需要我的代码来处理ie9而我找不到另一种方法,尽管我还没有测试过它。

在我得到结果之前,所有似乎都工作得很好,当我注意到我的所有路径都比最初的svg图中更粗。所以,试着找出我做错了什么,我开始对http://canvg.github.io/canvg/examples/index.htm进行小测试。然后,当我注意到如果我没有将内容或css文件中的属性fill设置为none,那么路径就比一个像素厚。由于我的svg图在一个单独的css文件中有一些样式,我试图将它们弄平(我从Convert embedded SVG to PNG in-place获取了这个想法):

function flatten_svg_element_css(target){
    if (target.nodeType != Node.TEXT_NODE) {
        var cssStyle = window.getComputedStyle(target);
        if (cssStyle) {
            var fillStyle = '';
            if( cssStyle.getPropertyValue('fill') == 'none' && cssTyle.getPropertyValue('stroke') == 'rgb(0, 0, 0)'){
                fillStyle = 'fill:none; stroke:rgb(0, 0, 0);';
            }
            target.style.cssText = fillStyle + cssStyle.cssText;
        }
    }
}

function flatten_svg_css(target) {
    for (var i = 0; i < target.childNodes.length; i++) {
        var child = target.childNodes[i];
        if (child.childNodes != null && child.childNodes.length > 0) {
            flatten_svg_css(child);
        }
        else{
            flatten_svg_element_css(child);
        }
    }
}

但它似乎永远不会进入条件cssStyle.getPropertyValue('fill') == 'none' && cssTyle.getPropertyValue('stroke') == 'rgb(0, 0, 0)

target是路径时,函数getPropertyValue('fill')会返回rgb(0, 0, 0)而不是none。但是,如果我使用Firebug window.getComputedStyle(d3.select('.domain').node()).getPropertyValue('fill')直接测试该元素,我将值赋予none

这是我想要转换为png图像的svg图。该图表是使用库“dc.js”生成的:

<svg width="1166" height="317">
    <g>
        <g class="grid-line horizontal" transform="translate(50,10)">
            <line x1="1" y1="265" x2="1066" y2="265" opacity="0" />
            <line x1="1" y1="239" x2="1066" y2="239" opacity="0" />
            <line x1="1" y1="212" x2="1066" y2="212" opacity="0" />
            <line x1="1" y1="186" x2="1066" y2="186" opacity="0" />
            <line x1="1" y1="159" x2="1066" y2="159" opacity="0" />
            <line x1="1" y1="133" x2="1066" y2="133" opacity="0" />
            <line x1="1" y1="106" x2="1066" y2="106" opacity="0" />
            <line x1="1" y1="80" x2="1066" y2="80" opacity="0" />
            <line x1="1" y1="53" x2="1066" y2="53" opacity="0" />
            <line x1="1" y1="27" x2="1066" y2="27" opacity="0" />
            <line x1="1" y1="0" x2="1066" y2="0" opacity="0" />
        </g>
        <g class="chart-body" transform="translate(50, 10)"
            clip-path="url(http://127.0.0.1:1234/index.jsp?gwt.codesvr=127.0.0.1:9997#analysis_charts_first_chart-clip)">
            <g class="stack _0">
                <rect class="bar" fill="#1f77b4" y="133" height="132" width="532"
                    x="1">
                    <title>ds1 - missing: 50%</title>
                </rect>
                <rect class="bar" fill="#1f77b4" y="133" height="132" width="532"
                    x="534">
                    <title>ds3 - missing: 50%</title>
                </rect>
            </g>
            <g class="stack _1">
                <rect class="bar" fill="#ffbb78" y="87" height="46" width="532"
                    x="1">
                    <title>ds1 - something else: 17%</title>
                </rect>
                <rect class="bar" fill="#ffbb78" y="133" height="0" width="532"
                    x="534">
                    <title>ds3 - something else: 0%</title>
                </rect>
            </g>
            <g class="stack _2">
                <rect class="bar" fill="#aec7e8" y="0" height="87" width="532"
                    x="1">
                    <title>ds1 - total: 33%</title>
                </rect>
                <rect class="bar" fill="#aec7e8" y="0" height="133" width="532"
                    x="534">
                    <title>ds3 - total: 50%</title>
                </rect>
            </g>
        </g>
        <g class="axis x" transform="translate(50,275)">
            <g class="tick" style="opacity: 1;" transform="translate(266.5,0)">
                <line y2="6" x2="0" />
                <text dy=".71em" style="text-anchor: middle;" y="9" x="0">ds1
                </text>
            </g>
            <g class="tick" style="opacity: 1;" transform="translate(799.5,0)">
                <line y2="6" x2="0" />
                <text dy=".71em" style="text-anchor: middle;" y="9" x="0">ds3
                </text>
            </g>
            <path class="domain" d="M0,6V0H1066V6" />
        </g>
        <text class="x-axis-label" transform="translate(583,305)"
            text-anchor="middle">Datasets</text>
        <g class="axis y" transform="translate(50,10)">
            <g class="tick" style="opacity: 1;" transform="translate(0,265)">
                <line x2="-6" y2="0" />
                <text dy=".32em" style="text-anchor: end;" x="-9" y="0">0%</text>
            </g>
            <g class="tick" style="opacity: 1;" transform="translate(0,239)">
                <line x2="-6" y2="0" />
                <text dy=".32em" style="text-anchor: end;" x="-9" y="0">10%</text>
            </g>
            <g class="tick" style="opacity: 1;" transform="translate(0,212)">
                <line x2="-6" y2="0" />
                <text dy=".32em" style="text-anchor: end;" x="-9" y="0">20%</text>
            </g>
            <g class="tick" style="opacity: 1;" transform="translate(0,186)">
                <line x2="-6" y2="0" />
                <text dy=".32em" style="text-anchor: end;" x="-9" y="0">30%</text>
            </g>
            <g class="tick" style="opacity: 1;" transform="translate(0,159)">
                <line x2="-6" y2="0" />
                <text dy=".32em" style="text-anchor: end;" x="-9" y="0">40%</text>
            </g>
            <g class="tick" style="opacity: 1;" transform="translate(0,133)">
                <line x2="-6" y2="0" />
                <text dy=".32em" style="text-anchor: end;" x="-9" y="0">50%</text>
            </g>
            <g class="tick" style="opacity: 1;" transform="translate(0,106)">
                <line x2="-6" y2="0" />
                <text dy=".32em" style="text-anchor: end;" x="-9" y="0">60%</text>
            </g>
            <g class="tick" style="opacity: 1;" transform="translate(0,80)">
                <line x2="-6" y2="0" />
                <text dy=".32em" style="text-anchor: end;" x="-9" y="0">70%</text>
            </g>
            <g class="tick" style="opacity: 1;" transform="translate(0,53)">
                <line x2="-6" y2="0" />
                <text dy=".32em" style="text-anchor: end;" x="-9" y="0">80%</text>
            </g>
            <g class="tick" style="opacity: 1;" transform="translate(0,27)">
                <line x2="-6" y2="0" />
                <text dy=".32em" style="text-anchor: end;" x="-9" y="0">90%</text>
            </g>
            <g class="tick" style="opacity: 1;" transform="translate(0,0)">
                <line x2="-6" y2="0" />
                <text dy=".32em" style="text-anchor: end;" x="-9" y="0">100%</text>
            </g>
            <path class="domain" d="M-6,0H0V265H-6" />
        </g>
        <text transform="translate(12,142.5),rotate(-90)" class="y-axis-label y-label"
            text-anchor="middle">Data Quality</text>
    </g>
    <defs>
        <clipPath id="analysis_charts_first_chart-clip">
            <rect width="1066" height="265" transform="translate(-0, -0)" />
        </clipPath>
    </defs>
</svg>

所以我想在尝试递归地展平样式时我做错了。

0 个答案:

没有答案