2017-08-30 77 views
0

在瀏覽器窗口中,我有一個包含圖像的svg。 我也在這個頁面上放了一些圈子。 當我調整窗口大小時,圖像調整大小正確,但圓圈仍保持其絕對位置。如何在調整窗口大小時設置svg以更改位置?

設置它的最佳方法是什麼? 如果可能,圈子不應調整大小,而應改變其位置。

<!DOCTYPE html> 
<html> 
    <head> 
     <meta http-equiv="content-type" content="text/html; charset=UTF-8"> 
     <meta name="robots" content="noindex, nofollow"> 
     <meta name="googlebot" content="noindex, nofollow"> 

     <style> 
      html,body{padding:0px; margin:0px; height:100%; width:100%;} 
     </style> 

     <script type="text/javascript" src="http://d3js.org/d3.v3.min.js"></script> 

     <title>Test</title> 

     <script type='text/javascript'>//<![CDATA[ 

      window.onload=function() 
      { 

       function click() 
       { 
        // Ignore the click event if it was suppressed 
        if (d3.event.defaultPrevented) return; 

        // Extract the click location 
        var point = d3.mouse(this) 
        , p = {x: point[0], y: point[1] }; 


        //Append the group 
        var newGroup = d3.select("svg").append("g") 
         .attr("transform", "translate(" + p.x + "," + p.y + ")") 
         .attr("drgg", "") 
         .style("cursor", "pointer") 
         .on("mouseup", selremove) 
         .call(drag); 

        //Append the circle 
        var newCircle = newGroup.append("circle") 
         .attr("r", "25") 
         .attr("class", "dot") 
         .style("stroke", "#999999") 
         .style("fill", "#66B132") 
         .attr("opacity", 0.8); 

        //Append the text 
        var newText = newGroup.append("text") 
         .text("43") 
         .style("fill", "#FFFFFF") 
         .style("font-family", "Arial") 
         .style("font-size", "24px") 
         .style("text-anchor", "middle") 
         .style("alignment-baseline", "central") 
         .style("readonly", "true"); 

       } 


       //Create the SVG 
       var svg = d3.select("body").append("svg") 
        .attr("width", "100%") 
        .attr("height", "100%") 
        .on("click", click); 

       //Add a background to the SVG 
       svg.append("rect") 
        .attr("width", "100%") 
        .attr("height", "100%") 
        .style("stroke", "#999999") 
        .style("fill", "#F6F6F6") 

       //Add a Background-Picture 
       var pPic = d3.select("body").select("svg").append("image") 
        .attr("opacity", 1.0) 
        .attr("width", "100%") 
        .attr("height", "100%") 
        .attr("preserveAspectRatio", "xMidyMid") 
        .attr("xlink:href", "https://m.bmw.de/content/dam/bmw/common/all-models/m-series/x6m/2014/model-card/X6-M-F86_ModelCard.png") 

       //Move or delete 
       function selremove() { 
        if (d3.select(this).attr("drgg") == "") 
        { 
        d3.select(this).remove(); 
        } 
        else 
        { 
        d3.select(this).attr("drgg", ""); 
        } 
       } 

       function showinfo() { 
        //d3.select(this).attr("fill", "#000000"); 
        var point = d3.mouse(this) 
        , p = {x: point[0], y: point[1] }; 

        var newRect = svg.append("rectangle") 
        .attr("transform", "translate(" + p.x + "," + p.y + ")") 
        .attr("width", "25") 
        .attr("height", "25") 
        .style("stroke", "#999999") 
        .style("fill", "#FFFA83") 
        .attr("opacity", 1.0); 
       } 

       // Define drag beavior 
       var drag = d3.behavior.drag() 
        .on("drag", dragmove); 

       function dragmove() 
       { 
        var x = d3.event.x; 
        var y = d3.event.y; 

        d3.select(this) 
        .attr("transform", "translate(" + x + "," + y + ")") 
        .attr("drgg", "1"); 

       } 
      }//]]> 

     </script> 
    </head> 
    <body> 
     <script> 
      // tell the embed parent frame the height of the content 
      if (window.parent && window.parent.parent){ 
      window.parent.parent.postMessage(["resultsFrame", { 
       height: document.body.getBoundingClientRect().height, 
       slug: "None" 
      }], "*") 
      } 
     </script> 
    </body> 
</html> 
+2

看來你的代碼有問題。但是,除非我們有[可以重現問題的代碼或信息](// stackoverflow.com/help/mcve),否則我們無能爲力。否則,我們只是盲目猜測。 –

+4

請在您的問題中添加[mcve] –

回答

1

我首先想到這可以用相對單位來實現,但SVG的縱橫比變化會讓你進入熱水。所以最好的方法似乎是將SVG viewBox固定到原始圖像尺寸。這些需要事先知道,因爲SVGImageElement不能從圖像源本身提取它們。

爲此付出的代價是每次調整窗口大小時都必須調整疊加圈子。

本示例不涉及拖動功能。

//an event counter 
var counter = 0; 

//image metadata 
var pData = { 
    url: "https://m.bmw.de/content/dam/bmw/common/all-models/m-series/x6m/2014/model-card/X6-M-F86_ModelCard.png", 
    width: 890, 
    height: 501 
} 

//Create the SVG with viewBox at native image size 
var svg = d3.select("body").append("svg") 
    .attr("xmlns:xlink", "http://www.w3.org/1999/xlink") 
    .attr("width", "100%") 
    .attr("height", "100%") 
    .attr('viewBox', "0 0 " + pData.width + " " + pData. height) 
    .attr("preserveAspectRatio", "xMidyMid") 
    .on("click", click); 

var defs = svg.append("defs"); 

//Add a Background-Picture 
var pPic = d3.select("body").select("svg").append("image") 
    .attr("width", "100%") 
    .attr("height", "100%") 
    .attr("xlink:href", pData.url) 

function click() { 
    // Ignore the click event if it was suppressed 
    if (d3.event.defaultPrevented) return; 

    // Extract the click location relative to SVG 
    var point = d3.mouse(this); 
    // get SVG scaling 
    var ctm = svg.node().getScreenCTM(), 
     scale = "scale(" + (1/ctm.a) + "," + (1/ctm.d) + ")"; 

    // Unique id 
    var id = "dot" + counter++; 

    //Append the group offscreen 
    var newGroup = defs.append("g") 
     .attr("id", id) 
     .attr("transform", scale); 

    //Append the circle 
    var newCircle = newGroup.append("circle") 
     .attr("r", "25") 
     .attr("class", "dot") 
     .style("stroke", "#999999") 
     .style("fill", "#66B132") 
     .attr("opacity", 0.8); 

    //Append the text 
    var newText = newGroup.append("text") 
     .text("43") 
     .style("fill", "#FFFFFF") 
     .style("font-family", "Arial") 
     .style("font-size", "24px") 
     .style("text-anchor", "middle") 
     .style("alignment-baseline", "central") 
     .style("readonly", "true"); 

    // indirect rendering with a new viewport 
    svg.append("use") 
     .attr("xlink:href", "#" + id) 
     .attr("x", point[0]) 
     .attr("y", point[1]); 
} 

// adjust group sizes on window resize 
var resize; 
window.addEventListener("resize", function() { 
    clearTimeout(resize); 
    resize = setTimeout(function() { 
     var ctm = svg.node().getScreenCTM(); 
     // select all groups before they are repositioned 
     defs.selectAll('g').attr("transform", "scale(" + (1/ctm.a) + "," + (1/ctm.d) + ")"); 
    }, 100); 
}); 
+0

謝謝ccprog。這看起來不錯。只是錯過了保持比例。應該設置哪個元素? – masterkey

+0

我改變了我的答案,以考慮縱橫比的變化。 – ccprog

+0

就是這樣。謝謝! – masterkey

相關問題