각도와 치수가 주어지면 사각형 주변을 따라 좌표를 찾으십시오.

StackOverflow https://stackoverflow.com/questions/1026763

  •  06-07-2019
  •  | 
  •  

문제

주어진 피벗 (또는 원점)을 중심으로 아이콘이 회전하는 스크립트를 작성하고 있습니다. 타원 주위의 아이콘을 회전시키는 데이 작업을 수행 할 수 있었지만 특정 폭, 높이 및 원점의 사각형 주변을 주변으로 이동하고 싶습니다.

내 현재 코드가 각각의 각도 정수가있는 배열에 모든 코디를 저장 하고이 코드를 재사용하는 것이 훨씬 쉽게 작업하기 때문에 이런 식으로 수행하고 있습니다.

누군가 나에게 100x150 사각형의 예를 제시 할 수 있다면 그것은 좋을 것입니다.

편집하다: 명확히하기 위해, 회전함으로써 나는 모양의 주변 (또는 궤도)을 주위로 움직이는 것을 의미합니다.

도움이 되었습니까?

해결책

사각형의 크기를 알고 전체 각도 간격을 네 가지 다른 것으로 분할해야하므로 사각형의 중심에서 나오는 광선이 직사각형의 오른쪽, 상단, 왼쪽 또는 하단이 교차하는지 알 수 있습니다.

각도가 : -atan (d/w) <alfa <atan (d/w) 인 경우 광선은 사각형의 오른쪽을 교차시킵니다. 그런 다음 사각형의 중심에서 오른쪽으로 X- 변위가 d/2라는 것을 알고 있기 때문에 d/2로 나눈 변위 dy는 tan (alfa)입니다.

dy = d/2 * tan (Alfa)

다른 3 개의 각도 간격으로이를 유사하게 처리합니다.

좋아, 여기 간다. 너비 w와 깊이 d가있는 직장이 있습니다. d. 가운데에는 중심점이 있습니다, cp. 각도 알파의 다른 값에 대해 p를 계산하고 싶다고 가정합니다.

alt text

사각형을 네 개의 다른 영역 또는 각도 간격 (1 ~ 4)으로 나누었습니다. 위에서 언급 한 간격은 오른쪽의 첫 번째 간격입니다. 나는 이것이 당신에게 의미가 있기를 바랍니다.

먼저 각도 간격을 계산해야하며 W와 D에 의해 완전히 결정됩니다. Alfa가 가지고있는 값에 따라 CP에서 P 로의 "광선"이 사각형의 상단, 하단, 오른쪽 또는 왼쪽을 교차하는 경우 P를 계산하십시오.

건배

다른 팁

이것은 Pebble Smartwatch에서 작업하고 검증되었지만 의사 코드로 수정되었습니다.

struct GPoint {
  int x;
  int y;
}

// Return point on rectangle edge.  Rectangle is centered on (0,0) and has a width of w and height of h
GPoint getPointOnRect(int angle, int w, int h) {
  var sine = sin(angle), cosine = cos(angle);   // Calculate once and store, to make quicker and cleaner
  var dy = sin>0 ? h/2 : h/-2;                  // Distance to top or bottom edge (from center)
  var dx = cos>0 ? w/2 : w/-2;                  // Distance to left or right edge (from center)
  if(abs(dx*sine) < abs(dy*cosine)) {           // if (distance to vertical line) < (distance to horizontal line)
    dy = (dx * sine) / cosine;                  // calculate distance to vertical line
  } else {                                      // else: (distance to top or bottom edge) < (distance to left or right edge)
    dx = (dy * cosine) / sine;                  // move to top or bottom line
  }
  return GPoint(dx, dy);                        // Return point on rectangle edge
}


Use:
rectangle_width  = 100;
rectangle_height = 150;
rectangle_center_x = 300;
rectangle_center_y = 300;
draw_rect(rectangle_center_x - (rectangle_width/2), rectangle_center_y - (rectangle_center_h/2), rectangle_width, rectangle_height);
GPoint point = getPointOnRect(angle, rectangle_width, rectangle_height);
point.x += rectangle_center_x;
point.y += rectangle_center_y;
draw_line(rectangle_center_x, rectangle_center_y, point.x, point.y);

매개 변수로 각도를 사용 하여이 작업을 수행하는 한 가지 간단한 방법은 사각형의 범위를 사용하여 x와 y 값을 단순히 클립하는 것입니다. 다시 말해, 아이콘이 원형 또는 타원 경로 주위에서 회전하는 것처럼 위치를 계산 한 다음 다음을 적용합니다.

(x 축 길이와 xaxis의 x 축 길이와 yaxis의 y 축 길이가있는 축-정렬 된 사각형을 가정) :

if (X > XAxis/2)    
         X = XAxis/2;

if (X < 0 - XAxis/2)
         X = 0 - XAxis/2;

if (Y > YAxis/2)    
         Y = YAxis/2;

if (Y < 0 - YAxis/2)    
         Y = 0 - YAxis/2;

이 접근법의 문제점은 각도가 완전히 정확하지 않으며 사각형 주변의 속도가 일정하지 않다는 것입니다. 모서리의 사각형을 진동하는 타원을 모델링하면 효과를 최소화 할 수 있지만 부드럽고 일정한 속도의 "궤도를 찾고 있다면"이 방법은 적절하지 않습니다.

당신이 지구가 태양 주위로 회전하는 것처럼 회전한다고 생각한다면 (자기 회전이 아니라 ... 그래서 당신의 질문은 사각형의 가장자리를 따라 미끄러지는 방법에 관한 것입니까?)

그렇다면 시도해 볼 수 있습니다.

# pseudo coode
for i = 0 to 499
  if i < 100:  x++
  else if i < 250: y--
  else if i < 350: x--
  else y++

  drawTheIcon(x, y)

업데이트: (아래 의견을 참조하십시오)

각도를 사용하려면 한 줄이 있습니다

y / x = tan(th)       # th is the angle

다른 줄은 수평이거나 수직이므로 간단합니다. 예를 들어, x = 50이며 위의 선에 넣어 y를 얻을 수 있습니다. 수평선과 수직선의 교차로를 위해 그렇게하십시오 (예 : 각도는 60도이며 "북동쪽"을 촬영합니다 ... 이제 두 점이 있습니다. 그러면 원점에 가장 가까운 지점은 사각형 먼저).

a 2D 변환 매트릭스. 많은 언어 (예 : Java)는 이것을 기본적으로 지원합니다 (친화적 변형). 그렇지 않으면, 한 번 회전을하고, 잘 디버깅하고, 영원히 사용하는 일상을 작성하십시오. 나는 그들 중 5 개가 다른 언어로 작성되어야합니다.

간단히 회전을 할 수 있으면, 라인 라인 교차로. 두 줄을 교차하여 궤도 아이콘의 중심을 찾으십시오.

  1. 당신이 원하는 각도에서 회전 중심의 광선
  2. 네면 중 하나는 원하는 각도 (4 개의 사분면)에 의해 경계됩니다.

직사각형과 회전 중심이있는 종이 조각에 스케치를 그립니다. 먼저 조정 시스템의 원점에서 사각형을 중앙으로 번역하십시오 (번역 매개 변수를 기억하십시오. 나중에 번역을 뒤집어 야합니다). 측면이 좌표 축과 평행하게되도록 사각형을 회전시킵니다 (동일한 이유).

이제 원점에서 알려진 각도가있는 삼각형이 있고, 반대쪽은 알려진 길이 (사각형의 한쪽 길이의 절반)입니다.

- 삼각형을 해결하십시오

- 회전을 취소하십시오

- 번역을 취소하십시오

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top