1

내 SVG 기반 웹 응용 프로그램에서 사용자는 많은 수의 도형 (심지어 800 이상)을 선택할 수 있습니다. &은 화면 상으로 움직입니다. 이것은 프레임 속도에 심각한 영향을 미친다 고 생각할 수 있습니다. requestAnimationFrame의 장점을 읽은 후, 어제부터 mousemove 기능에 통합하려고 시도한 이후로, & requestAnimationFrame 스로틀 조합을 사용하여 원활한 프레임 속도를 얻을 수 있기를 바랍니다.mousemove 이벤트에서 requestAnimationFrame을 사용하는 방법은 무엇입니까?

Here은에서 600 자형을 움직이는 jsFiddle입니다. 지금은 조절을 무시하고 함수에 requestAnimationFrame을 어떻게 병합 할 수 있습니까?

http://jsfiddle.net/rehankhalid/5t5pX/

HTML 코드

<svg width="1200" height="800"> 
<symbol> 
    <g id="symbol1"> 
    <path fill="#3ab6d1" d="M27.7,1.1C16-2,3.9,5.1,0.8,16.9s4,23.8,15.7,26.9c11.7,3.1,23.8-4,26.9-15.7C46.6,16.3,39.6,4.2,27.7,1.1z M38.3,26.9C36,35.7,26.9,41,18,38.7C9.1,36.4,3.8,27.3,6.1,18.5C8.4,9.6,17.5,4.3,26.4,6.6C35.3,9,40.6,18,38.3,26.9z"/> 
    <g fill="#d5e1db"> 
    <path d="m25.8,.8c2.5,.4 4.8,1.2 7,2.5l-2.9,4.6c-1.5-.8-3.1-1.4-4.8-1.7l.7-5.4z"/> 
    <path d="m13.9,2.2l1.7,5.1c-1.5,.7-3,1.5-4.3,2.7l-3.8-3.9c.9-.8 1.9-1.5 2.9-2.2 1.2-.7 2.3-1.3 3.5-1.7z"/> 
    </g> 
    <path fill="#196275" d="m26.4,38.5l1.8,5.2c-2.5,.7-4.9,.9-7.4,.8l.6-5.4c1.6,0 3.3-.2 5-.6z"/> 
    <path fill="#42aec2" d="M6.1,18.4C8.4,9.5,17.5,4.2,26.4,6.5S40.7,18,38.4,26.8C36,35.7,26.9,41,18,38.7C9.1,36.3,3.7,27.2,6.1,18.4 z"/> 
    <path fill="#d2dfdd" d="m28.7,25.9l.5-4.9 9.5-1.3c0,.3 .1,.6 .2,.8 .4,2.9 0,5.8-1,8.3l-9.2-2.9z"/> 
    <path fill="#1b6273" d="m19.7,29.3h4.9l2.1,9.4c-.3,.1-.6,.2-.8,.2-2.9,.6-5.7,.5-8.4-.3l2.2-9.3z"/> 
    <path fill="#368098" d="m15.9,25.8l3.6,3.4-4.8,8.3c-.3-.1-.5-.3-.8-.4-2.6-1.5-4.6-3.5-6-5.9l8-5.4z"/> 
    <path fill="#d2dfdd" d="m18.6,16.5l-3,3.9-8.7-4c.1-.3 .2-.5 .3-.8 1.2-2.7 3.1-4.9 5.3-6.5l6.1,7.4z"/> 
    <path fill="#bde2e9" d="m26.4,32.1l-8.4-.5-4.9-6.8 2.3-8 7.7-3.2 7.3,4 1.5,8.2-5.5,6.3z"/> 
    </g> 
</symbol> 
<g id="default"> 
<g id="my-element"> 

</g> 
</g> 


<g id="draggroup"> 

</g> 

</svg> 

자바 스크립트

document.addEventListener('mousedown', mousedown, false); 


     var element = document.getElementById('my-element'); 
     var defaultg = document.getElementById('default'); 
     var mainsvg = document.getElementsByTagName('svg')[0]; 
     var draggroup = document.getElementById('draggroup'); 
     var svgns = "http://www.w3.org/2000/svg"; 



     var x = 0, y = 0; 
     var scale = '0.25'; 
     for (var i = 0; i < 600; i++) { 
      var useelement = document.createElementNS(svgns, "use"); 
      useelement.setAttributeNS('http://www.w3.org/1999/xlink', 'href', '#symbol1'); 
      useelement.setAttribute('transform', 'translate(' + x + ',' + y + ') scale(' + scale + ')'); 

      x += 12; 
      if (x === 240) { 
       x = 0; 
       y += 12; 
      } 

      element.appendChild(useelement); 

     } 


     var bbox = element.getBBox(); 
     var selectionRect = document.createElementNS(svgns, "rect"); 
     selectionRect.setAttribute('id', 'selectionrect'); 
     selectionRect.setAttribute('x', bbox.x); 
     selectionRect.setAttribute('y', bbox.y); 
     selectionRect.setAttribute('width', bbox.width); 
     selectionRect.setAttribute('height', bbox.height); 
     selectionRect.setAttribute('fill', 'grey'); 
     selectionRect.setAttribute('opacity', '0.2'); 

     draggroup.appendChild(selectionRect); 


     var dx = 0, dy = 0, mx = 0, my = 0; 
     var rectdx = 0, rectdy = 0; 
     var elementdx = 0, elementdy = 0; 

     function getSvgCordinates(event) { 
      var m = mainsvg.getScreenCTM(); 
      var p = mainsvg.createSVGPoint(); 
      var x, y; 

      x = event.pageX; 
      y = event.pageY; 

      p.x = x; 
      p.y = y; 
      p = p.matrixTransform(m.inverse()); 

      x = p.x; 
      y = p.y; 

      x = parseFloat(x.toFixed(3)); 
      y = parseFloat(y.toFixed(3)); 

      return {x: x, y: y}; 
     } 

     function mousedown(event) { 

      if (event.target.id === 'selectionrect') { 
       var svgXY = getSvgCordinates(event); 
       mx = svgXY.x; // mouse down x 
       my = svgXY.y;// mouse down y 


       draggroup.appendChild(element); 

       document.addEventListener('mousemove', mousemove, false); 
       document.addEventListener('mouseup', mouseup, false); 
      } 
     } 

     function mouseup() { 
      document.removeEventListener('mousemove', mousemove, false); 
      document.removeEventListener('mouseup', mouseup, false); 

      draggroup.setAttribute('transform', 'translate(0,0)'); 

      rectdx += dx; 
      rectdy += dy; 
      elementdx += dx; 
      elementdy += dy; 

      selectionRect.setAttribute('transform', 'translate(' + rectdx + ',' + rectdy + ')'); 
      element.setAttribute('transform', 'translate(' + elementdx + ',' + elementdy + ')'); 

      defaultg.appendChild(element); 

      dx = 0; 
      dy = 0; 
     } 

     function mousemove(event) { 
      var svgXY = getSvgCordinates(event); 
      dx = svgXY.x - mx; 
      dy = svgXY.y - my; 

      draggroup.setAttribute('transform', 'translate(' + dx + ',' + dy + ')'); 

     } 
+0

참조 : http://www.html5rocks.com/en/tutorials/speed/animations/ –

답변

1

기본적으로, 당신은 다른 함수에 draggroup.setAttribute() 통화를 이동해야 할 것입니다. 마우스가 아래로 움직일 때만 움직 이기만하면 드래그 여부를 나타내는 다른 변수를 추가하고 그럴 경우 requestAnimationFrame 만 호출하면됩니다.

var isDragging = false; 
function update() { // New function 
    if (isDragging) { 
    requestAnimationFrame(update); // Call self again, if still dragging 
    } 
    draggroup.setAttribute('transform', 'translate(' + dx + ',' + dy + ')'); 
} 
function mousedown(event) { 
    if (event.target.id === 'selectionrect') { 
    isDragging = true; 
    requestAnimationFrame(update); // Start animation loop 
    // existing logic here... 
    } 
} 
function mouseup() { 
    isDragging = false; 
    // existing logic here... 
} 

당신은 이미 별도의 변수 그룹 (dx, dy)에 대한 업데이트 된 위치를 저장하기 때문에 mousemove()에서 draggroup.setAttribute() 호출을 제거하고 위의 수정을 추가, 당신은 잘해야있어!

관련 문제