그림을 부드럽게하는 가장 좋은 방법은 베 제르 곡선을 사용하는 것입니다. 여기 내 코드가있다. Apple의 개발 사이트에서 찾은 수정 된 버전이지만 원래 링크가 기억 나지 않습니다.
CGPoint drawBezier(CGPoint origin, CGPoint control, CGPoint destination, int segments)
{
CGPoint vertices[segments/2];
CGPoint midPoint;
glDisable(GL_TEXTURE_2D);
float x, y;
float t = 0.0;
for(int i = 0; i < (segments/2); i++)
{
x = pow(1 - t, 2) * origin.x + 2.0 * (1 - t) * t * control.x + t * t * destination.x;
y = pow(1 - t, 2) * origin.y + 2.0 * (1 - t) * t * control.y + t * t * destination.y;
vertices[i] = CGPointMake(x, y);
t += 1.0/(segments);
}
//windowHeight is the height of you drawing canvas.
midPoint = CGPointMake(x, windowHeight - y);
glVertexPointer(2, GL_FLOAT, 0, vertices);
glDrawArrays(GL_POINTS, 0, segments/2);
return midPoint;
}
3 점을 기준으로 그려집니다. 컨트롤은 중간 지점이며 반환해야합니다. 새로운 중간 점은 이전과 다를 것입니다. 또한 위의 코드를 살펴 본다면 라인의 절반 만 그릴 것입니다. 다음 스트로크가 입력됩니다. 필수 항목입니다. 이 함수를 호출 내 코드 (위의 C에,이의 Obj-C에) :
//Invert the Y axis to conform the iPhone top-down approach
invertedYBegCoord = self.bounds.size.height - [[currentStroke objectAtIndex:i] CGPointValue].y;
invertedYEndCoord = self.bounds.size.height - [[currentStroke objectAtIndex:i+1] CGPointValue].y;
invertedYThirdCoord = self.bounds.size.height - [[currentStroke objectAtIndex:i+2] CGPointValue].y;
//Figure our how many dots you need
count = MAX(ceilf(sqrtf(([[currentStroke objectAtIndex:i+2] CGPointValue].x - [[currentStroke objectAtIndex:i] CGPointValue].x)
* ([[currentStroke objectAtIndex:i+2] CGPointValue].x - [[currentStroke objectAtIndex:i] CGPointValue].x)
+ ((invertedYThirdCoord - invertedYBegCoord) * (invertedYThirdCoord - invertedYBegCoord)))/pointCount), 1);
newMidPoint = drawBezier(CGPointMake([[currentStroke objectAtIndex:i] CGPointValue].x, invertedYBegCoord), CGPointMake([[currentStroke objectAtIndex:i+1] CGPointValue].x, invertedYEndCoord), CGPointMake([[currentStroke objectAtIndex:i+2] CGPointValue].x, invertedYThirdCoord), count);
int loc = [currentStroke count]-1;
[currentStroke insertObject:[NSValue valueWithCGPoint:newMidPoint] atIndex:loc];
[currentStroke removeObjectAtIndex:loc-1];
현재로 '제어'를 거꾸로 아이 패드 포인트를 기준으로 중간 점을 얻고, 설정합니다 그 코드 포인트.
가장자리를 부드럽게 만듭니다. 이제 선폭과 관련하여 그 그림의 속도를 찾아야합니다. 선의 길이를 찾는 것이 가장 쉽습니다. 이는 컴포넌트 수학을 사용하여 쉽게 수행됩니다. 필자는 코드를 가지고 있지 않지만, here은 물리 사이트의 구성 요소 수학을위한 입문서입니다. 또는 (위) 카운트를 몇 가지 숫자로 나누면 라인이 얼마나 두꺼운 지 알아볼 수 있습니다 (카운트는 컴포넌트 수학을 사용합니다).
필자는 명확하지 않은 경우를 대비하여 currentStroke라는 배열에 포인트 데이터를 저장합니다.
필요한 것이 전부입니다.
편집 :
포인트를 저장하려면 사용합니다 touchesBegin 및 touchesEnd :
- (void) touchesBegan:(NSSet*)touches withEvent:(UIEvent*)event
{
self.currentStroke = [NSMutableArray array];
CGPoint point = [ [touches anyObject] locationInView:self];
[currentStroke addObject:[NSValue valueWithCGPoint:point]];
[self draw];
}
- (void) touchesMoved:(NSSet*)touches withEvent:(UIEvent*)event
{
CGPoint point = [ [touches anyObject] locationInView:self];
[currentStroke addObject:[NSValue valueWithCGPoint:point]];
[self draw];
}
- (void) touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event
{
CGPoint point = [ [touches anyObject] locationInView:self];
[currentStroke addObject:[NSValue valueWithCGPoint:point]];
[self draw];
}
거의가 전체 도면 응용 프로그램입니다. GL_Paint를 사용하고 있다면이 시스템이 구축 한 포인트 스프라이트를 이미 사용하고있는 것입니다.
대단히 고마워요,이게 정말 도움이됩니다. 그러나 코드의 두 번째 부분을 어디에서 구현해야할지 모르겠습니다. GLPaint 예제에는 사용자가 손가락을 움직일 때마다 호출되는 renderLineFromPoint : toPoint : 함수가 있습니다. 그 함수에 코드의 두 번째 부분을 넣어야합니까? – burki
또는 전체 코드를 추가 할 수 있습니까? 나는 완전한 방법을 의미합니다. 그것은 매우 친절합니다. – burki
touches 추가, touchesMoved 및 touchesEnd가 추가되었습니다. 꽤 많은 OpenGL 그리기 응용 프로그램이 게시됩니다. – Beaker