2013-04-19 7 views
1

나는 주어진 여백에 타원을 둘러싼 베 지어 곡선을 그릴려고 :프로그래밍 베 지어 또는 타원형 경로 타원의 일부를 그리기 - SVG와 raphael.js

Bezier path surrounding an ellipse

I을 이 프로그래밍 방식으로 달성하고 싶습니다, 그래서 만약 내가 타원 크기를 변경하면 커브가 따라옵니다. 나는이 기능을 만들어 놓은 순간

:

function bezierPathTopRounded(ellipse, margin) { 
    var box = ellipse.paper.getBBox(); 

    var leftX = box.x - margin; 

    var rightX = box.x + margin + box.width; 

    var y = box.y + box.height/2 - margin; 

    var p = "M "+ leftX + ", "+ y 
    + " C " //could be relative too 
    + (box.x - margin + (box.width/15) ) + ", " + (box.y + margin - (box.height/4.5) ) + " " 
    + (box.x + margin + box.width - (box.width/15) ) + ", " + (box.y + margin - (box.height/4.5)) + " " 
    + rightX +", " + y; 

    return p; 
} 

을하지만 그것이 어떤 타원으로 작동 할 수 있도록이 방향 점의 값을 계산하는 방법을 알아낼 수 없습니다 :

  • box.width/15
  • box.height는/4.5

fiddle with this example 있습니다.

간단한 해결책을 알아낼 수 없습니다 아직도 내가이 stackoverflow question을 읽어 봤는데, 내 예에서 동일한 시도했지만, 내가 '이제 ...

편집

을 무작위로 남아 타원형 A RC와 함께 노력하고, 그 결과는 베 지어 패스보다 worser입니다 :

Elliptical Arc test

은 내가 사용하는 기능이있다. 내가 마진을 제거하면 정확하게 타원을 따라 간다. 마침내 이것이 문제는 타원을 여백으로 어떻게 따라갈 수 있는가이다.

function borderPath(ellipse, margin, flag) { 
    var flag = flag == undefined ? 1 : 0; 

    var box = ellipse.paper.getBBox(); 

    var leftX = box.x - margin; 

    var rightX = box.x + margin + box.width; 

    var y = box.y + box.height/2; 
    y += (flag == 1) ? -margin : margin; 

    var rx = box.width/2 + margin; 
    var ry = box.height/2; 

    var p = "M "+ leftX + ", "+ y 
    + " A " 
    + rx + " " + ry 
    + " 0 0 "+ flag +" " 
    + rightX +", " + y; 

    return p; 
} 

updated fiddle here을 참조하십시오.

끔찍한 색깔에 대해 정말 유감입니다.

+0

왜 베 지어 : 여기

는 기능입니다? 적절한 크기/위치의 다른 부분 타원을 그려 보지 않겠습니까? –

+0

당신은 타원형 호를 가진 meen입니까? 나는 이것을 전에 시도했지만, 마진 때문에 더 이상 완벽한 타원이 될 수 없었습니다. 그리고 나는이 특정한 노선을 그릴 수있는 길이어야합니다. – soyuka

+0

예 타원형 호를 의미합니다. 동심원의 타원이 당신이 추구하는 효과를 내지 못할 수도 있다는 귀하의 요지를 보았지만 말입니다. 베 지어 곡선은 근사치 일 뿐이라고 생각합니다. 'box.width/15'와'box.height/4.5'는 어떻게 얻었습니까? 수학을 일반화하는 문제가 아닌가? –

답변

1

저는 타원과 그 여백에 따라 타원형 호를 만들었습니다. 직사각형으로 원하지 않는 부분을 단순히 숨기는 것 이상입니다.

function borderPath(ellipse, flag) { 
    var flag = flag == undefined ? 1 : flag; 

    var box = ellipse.paper.getBBox(); 

    var leftX = box.x; 

    var rightX = box.x + box.width; 

    var y = box.y + box.height/2; 

    var rx = box.width/2; 
    var ry = box.height/2; 

    var p = "M "+ leftX + ", "+ y 
    + " A " 
    + rx + " " + ry 
    + " 0 0 "+ flag +" " 
    + rightX +", " + y; 

    return p; 
} 
2

베 지어 곡선으로이 작업을 수행하려면 "잘못된"모양을 결정해야합니다. 베 지어 곡선은 원형 (확장, 타원형) 커브를 나타낼 수 없으며, 더 적은 수의 섹션을 사용하여 더 높은 정밀도로 폴리곤 수와 동일한 방식으로 매우 가까워 질 수 있습니다.

나는 원 근사 곡선 모두 각각 베 지어 곡선, http://pomax.github.io/bezierinfo/#circles_cubichttp://pomax.github.io/bezierinfo/#offsetting 내 프라이머에 베 지어 곡선을 사용하여 상쇄 설명하지만, 처음부터이 코딩하는 경우 특히 상쇄 당신은 무엇을 위해 그것을 필요로하는 경우 과잉 될 것입니다 당신은 당신의 본보기로 묘사합니다.

대신 Inkscape 또는 Illustrator를 실행하고 격자 오버레이를 켜고 타원 주위에 베 지어 곡선을 그릴 것을 권장합니다. 보기 좋게 만든 다음 좌표가 무엇인지 확인하고 캔버스 프로그램에 구현하기에 충분한 정보를 사용하십시오. 사람들이 "잘못 본 것"으로 가지 않는 한 당신은 아마 수학적으로 엄격하게 교정 할 필요가 없습니다. 괜찮을 것입니다.

+0

멋진 기사가 있습니다! 나는 그들이 완벽하게 맞을 수는 없다는 것에 동의하지만, 나의 예에서는 "틀린"것이 아니다. 그렇지 않습니까? 타원에 따라 애니메이션을 적용하고 싶기 때문에 Inkscape 등으로는이 작업을 수행 할 수 없습니다. 내 솔루션 지금까지 경로 (시작, 종료)에 대한 두 가지 기능이 있습니다. 이제 "완벽한"커브를 원한다면 타원형 호를 사용해야합니까? - 마진에 의해 잘려서 맞지 않을 것입니다. – soyuka

+0

타원형 호를 사용하면 두 반지름을 같은 양만큼 상쇄하는 한 아마도 충분할 것입니다. 예를 들어 타원이 (x, y, r1, r2)이고 타원의 절반, 예를 들어 10 픽셀의 오프셋을 원하면 arc (x, y, r1 + 10, r2 + 10, pi, 2)를 사용합니다. * pi), 마지막 두 개는 호의 시작 및 끝 각도를 나타냅니다. 여기서 문제는 Canvas2D를 사용하는 경우 현재 사용할 수있는 유일한 원호는 원호입니다. 타원형 호 명령 ("타원")은 마침내 업데이트 된 초안에 있습니다. (요청한 사람들 중 하나입니다. 현재 추가되었습니다. 매우 행복합니다.) 아직 지원되지 않습니다. –

+0

Raphael (svg no canvas) 그래서'A' path -'rx ry x 축 회전 large-arc-flag 스윕 플래그 xy') 그러나이 정보 덕분에 길을 찾도록 노력할 것입니다. – soyuka

0

타원형 패스를 그리는 데 베 지어 곡선을 사용하면 두통이 발생할 수 있습니다. 당신이 코멘트에서 말했듯이, RaphaelJS에서 잘 작동하는 경로 호를 사용하고 있습니다.

기대하는 모든 값, 특히 플래그에 관한 문서는 http://www.svgbasics.com/arcs.html에서 찾을 수 있습니다.

+0

나는 그 모든 것을 고마워하지만 베 지어를 사용하면 더 잘 작동합니다. – soyuka