2012-12-17 1 views
10

HTML5 캔버스에 많은 점을 그릴 필요가 있으며 꽤 오래 걸립니다. 내 코드는 다음과 같습니다.HTML5 캔버스 요소에서 많은 점의 드로잉 속도 향상

var points = getPoints() // Array of {x,y,color} 
var ctx = canvas.getContext("2d"); 

for (var i = 0; i < points.length; i++) { 
    ctx.fillStyle = points[i].color 
    ctx.beginPath() 
    ctx.arc(points[i].x, points[i].y, radius, 0, Math.PI * 2, true) 
    ctx.fill() } 

이 작업 속도를 향상시키기 위해 수행 할 수있는 작업이 궁금합니다. 나는 단지 5 개의 다른 색을 가지고있다. 예를 들어 포인트 목록을 정렬하여 점 당 1 시간 대신 ctx.fillStyle을 5 번만 변경하는 방식에 도움이 될까요? 예를 들어

+0

를 참조하십시오 점 [i] .x, 점 [i] .y, 반지름, 0, Math.PI * 2, true)'간단한 직사각형을 그려보십시오. (IMHO, 그것 ...) – ppeterka

+1

나는 그것을 시험해 보았다. 그렇다. 속도가 올라간다. 그게 어떻게 도움이되는지는 모르겠지만. – Nicolas

+1

필자가 피들을 설정하면 사람들이 그것을 조정하기가 더 쉬울 것이라고 생각합니다. 여기에 약간의 수정을 가하면 좀 더 빠르게 (어쩌면) 생각할 수 있습니다 -> [** FIDDLE **] (http : // jsfiddle .net/4WTaQ /) ... – adeneo

답변

13

대신 포인트 당 한 시간 ctx.fillStyle 5 회로 변경에 - 더 - 비행 나는 지점 목록을 정렬 양식을 도움이 될?

제 경험상 예 - .fillStyle을 자주 변경하는 것은 자주 비용이 많이 듭니다.

캔버스에 많은 수의 직사각형을 플로팅하는 코드가 있었고 자주 변하는 색상이 2 개 밖에없는 사각형을 그릴 시간이 자주 바뀌는 많은 색상으로 플로팅하는 것보다 훨씬 낫습니다. 어쨌든

, 당신은 단지 5 개 개의 서로 다른 색상이 있기 때문에 :

  1. 당신이 필요없이 대상 캔버스에 적절한 색 원 블럭 전송 다섯 원
  2. 사용 .drawImage()을 그릴 수되는 오프 스크린 캔버스 만들기를 호 좌표를 다시 계산하려면
  3. 을 루프 내부의 로컬 변수에 할당하여 반복해서 역 참조를 방지하십시오. 이 코드는 7 밀리 초에 400x400 크기의 캔버스에 3000 원을 받고있다 내 노트북에

:`ctx.arc (:

var colours = ['red', 'green', 'blue', 'yellow', 'magenta']; 
var n = colours.length; 
var r = 10; 
var d = r * 2; 

var off = document.createElement('canvas'); 
off.width = n * d; 
off.height = d; 
var ctx = off.getContext('2d'); 

for (var i = 0; i < n; ++i) { 
    ctx.fillStyle = colours[i]; 
    ctx.beginPath(); 
    ctx.arc(i * d + r, r, r, 0, 2 * Math.PI); 
    ctx.closePath(); 
    ctx.fill(); 
} 

var canvas = document.getElementById('canvas'); 
var ctx2 = canvas.getContext('2d'); 
var t0 = Date.now(); 
for (var i = 0; i < 3000; ++i) { 
    var c = Math.floor(n * Math.random()); 
    var x = Math.floor(canvas.width * Math.random()); 
    var y = Math.floor(canvas.height * Math.random()); 
    ctx2.drawImage(off, c * d, d, d, x - r, y - r, d, d); 
} 
var t1 = Date.now(); 
alert((t1 - t0) + "ms"); 

내가이 꽤 느린 줄 생각 http://jsfiddle.net/alnitak/Dpgts/

+0

와우, 내 것이 3ms에 있습니다. 인상적. 고마워요! – Nicolas

+0

@Stewie BTW, 서클이 겹치지 않으면'.putImageData'를 사용하여 속도를 크게 높일 수 있습니다. – Alnitak

+0

그들은 그렇지 않습니다. .drawImage() 대신에? – Nicolas