mirror of
https://github.com/zoriya/react-native-svg.git
synced 2026-05-28 04:55:12 +00:00
Port new GlyphContext, FontData, enums, props, Bezier and text rendering
This commit is contained in:
@@ -0,0 +1,242 @@
|
||||
/*
|
||||
|
||||
Erica Sadun, http://ericasadun.com
|
||||
|
||||
*/
|
||||
|
||||
#import "BaseGeometry.h"
|
||||
|
||||
#pragma mark - Conversion
|
||||
// Degrees from radians
|
||||
CGFloat DegreesFromRadians(CGFloat radians)
|
||||
{
|
||||
return radians * 180.0f / M_PI;
|
||||
}
|
||||
|
||||
// Radians from degrees
|
||||
CGFloat RadiansFromDegrees(CGFloat degrees)
|
||||
{
|
||||
return degrees * M_PI / 180.0f;
|
||||
}
|
||||
|
||||
#pragma mark - Clamp
|
||||
CGFloat Clamp(CGFloat a, CGFloat min, CGFloat max)
|
||||
{
|
||||
return fmin(fmax(min, a), max);
|
||||
}
|
||||
|
||||
CGPoint ClampToRect(CGPoint pt, CGRect rect)
|
||||
{
|
||||
CGFloat x = Clamp(pt.x, CGRectGetMinX(rect), CGRectGetMaxX(rect));
|
||||
CGFloat y = Clamp(pt.y, CGRectGetMinY(rect), CGRectGetMaxY(rect));
|
||||
return CGPointMake(x, y);
|
||||
}
|
||||
|
||||
|
||||
#pragma mark - General Geometry
|
||||
CGPoint RectGetCenter(CGRect rect)
|
||||
{
|
||||
return CGPointMake(CGRectGetMidX(rect), CGRectGetMidY(rect));
|
||||
}
|
||||
|
||||
CGFloat PointDistanceFromPoint(CGPoint p1, CGPoint p2)
|
||||
{
|
||||
CGFloat dx = p2.x - p1.x;
|
||||
CGFloat dy = p2.y - p1.y;
|
||||
|
||||
return sqrt(dx*dx + dy*dy);
|
||||
}
|
||||
|
||||
CGPoint RectGetPointAtPercents(CGRect rect, CGFloat xPercent, CGFloat yPercent)
|
||||
{
|
||||
CGFloat dx = xPercent * rect.size.width;
|
||||
CGFloat dy = yPercent * rect.size.height;
|
||||
return CGPointMake(rect.origin.x + dx, rect.origin.y + dy);
|
||||
}
|
||||
|
||||
#pragma mark - Rectangle Construction
|
||||
CGRect RectMakeRect(CGPoint origin, CGSize size)
|
||||
{
|
||||
return (CGRect){.origin = origin, .size = size};
|
||||
}
|
||||
|
||||
CGRect SizeMakeRect(CGSize size)
|
||||
{
|
||||
return (CGRect){.size = size};
|
||||
}
|
||||
|
||||
CGRect PointsMakeRect(CGPoint p1, CGPoint p2)
|
||||
{
|
||||
CGRect rect = CGRectMake(p1.x, p1.y, p2.x - p1.x, p2.y - p1.y);
|
||||
return CGRectStandardize(rect);
|
||||
}
|
||||
|
||||
CGRect OriginMakeRect(CGPoint origin)
|
||||
{
|
||||
return (CGRect){.origin = origin};
|
||||
}
|
||||
|
||||
CGRect RectAroundCenter(CGPoint center, CGSize size)
|
||||
{
|
||||
CGFloat halfWidth = size.width / 2.0f;
|
||||
CGFloat halfHeight = size.height / 2.0f;
|
||||
|
||||
return CGRectMake(center.x - halfWidth, center.y - halfHeight, size.width, size.height);
|
||||
}
|
||||
|
||||
CGRect RectCenteredInRect(CGRect rect, CGRect mainRect)
|
||||
{
|
||||
CGFloat dx = CGRectGetMidX(mainRect)-CGRectGetMidX(rect);
|
||||
CGFloat dy = CGRectGetMidY(mainRect)-CGRectGetMidY(rect);
|
||||
return CGRectOffset(rect, dx, dy);
|
||||
}
|
||||
|
||||
#pragma mark - Point Location
|
||||
CGPoint PointAddPoint(CGPoint p1, CGPoint p2)
|
||||
{
|
||||
return CGPointMake(p1.x + p2.x, p1.y + p2.y);
|
||||
}
|
||||
|
||||
CGPoint PointSubtractPoint(CGPoint p1, CGPoint p2)
|
||||
{
|
||||
return CGPointMake(p1.x - p2.x, p1.y - p2.y);
|
||||
}
|
||||
|
||||
#pragma mark - Cardinal Points
|
||||
CGPoint RectGetTopLeft(CGRect rect)
|
||||
{
|
||||
return CGPointMake(
|
||||
CGRectGetMinX(rect),
|
||||
CGRectGetMinY(rect)
|
||||
);
|
||||
}
|
||||
|
||||
CGPoint RectGetTopRight(CGRect rect)
|
||||
{
|
||||
return CGPointMake(
|
||||
CGRectGetMaxX(rect),
|
||||
CGRectGetMinY(rect)
|
||||
);
|
||||
}
|
||||
|
||||
CGPoint RectGetBottomLeft(CGRect rect)
|
||||
{
|
||||
return CGPointMake(
|
||||
CGRectGetMinX(rect),
|
||||
CGRectGetMaxY(rect)
|
||||
);
|
||||
}
|
||||
|
||||
CGPoint RectGetBottomRight(CGRect rect)
|
||||
{
|
||||
return CGPointMake(
|
||||
CGRectGetMaxX(rect),
|
||||
CGRectGetMaxY(rect)
|
||||
);
|
||||
}
|
||||
|
||||
CGPoint RectGetMidTop(CGRect rect)
|
||||
{
|
||||
return CGPointMake(
|
||||
CGRectGetMidX(rect),
|
||||
CGRectGetMinY(rect)
|
||||
);
|
||||
}
|
||||
|
||||
CGPoint RectGetMidBottom(CGRect rect)
|
||||
{
|
||||
return CGPointMake(
|
||||
CGRectGetMidX(rect),
|
||||
CGRectGetMaxY(rect)
|
||||
);
|
||||
}
|
||||
|
||||
CGPoint RectGetMidLeft(CGRect rect)
|
||||
{
|
||||
return CGPointMake(
|
||||
CGRectGetMinX(rect),
|
||||
CGRectGetMidY(rect)
|
||||
);
|
||||
}
|
||||
|
||||
CGPoint RectGetMidRight(CGRect rect)
|
||||
{
|
||||
return CGPointMake(
|
||||
CGRectGetMaxX(rect),
|
||||
CGRectGetMidY(rect)
|
||||
);
|
||||
}
|
||||
|
||||
#pragma mark - Aspect and Fitting
|
||||
CGSize SizeScaleByFactor(CGSize aSize, CGFloat factor)
|
||||
{
|
||||
return CGSizeMake(aSize.width * factor, aSize.height * factor);
|
||||
}
|
||||
|
||||
CGSize RectGetScale(CGRect sourceRect, CGRect destRect)
|
||||
{
|
||||
CGSize sourceSize = sourceRect.size;
|
||||
CGSize destSize = destRect.size;
|
||||
|
||||
CGFloat scaleW = destSize.width / sourceSize.width;
|
||||
CGFloat scaleH = destSize.height / sourceSize.height;
|
||||
|
||||
return CGSizeMake(scaleW, scaleH);
|
||||
}
|
||||
|
||||
CGFloat AspectScaleFill(CGSize sourceSize, CGRect destRect)
|
||||
{
|
||||
CGSize destSize = destRect.size;
|
||||
CGFloat scaleW = destSize.width / sourceSize.width;
|
||||
CGFloat scaleH = destSize.height / sourceSize.height;
|
||||
return fmax(scaleW, scaleH);
|
||||
}
|
||||
|
||||
CGFloat AspectScaleFit(CGSize sourceSize, CGRect destRect)
|
||||
{
|
||||
CGSize destSize = destRect.size;
|
||||
CGFloat scaleW = destSize.width / sourceSize.width;
|
||||
CGFloat scaleH = destSize.height / sourceSize.height;
|
||||
return fmin(scaleW, scaleH);
|
||||
}
|
||||
|
||||
CGRect RectByFittingRect(CGRect sourceRect, CGRect destinationRect)
|
||||
{
|
||||
CGFloat aspect = AspectScaleFit(sourceRect.size, destinationRect);
|
||||
CGSize targetSize = SizeScaleByFactor(sourceRect.size, aspect);
|
||||
return RectAroundCenter(RectGetCenter(destinationRect), targetSize);
|
||||
}
|
||||
|
||||
CGRect RectByFillingRect(CGRect sourceRect, CGRect destinationRect)
|
||||
{
|
||||
CGFloat aspect = AspectScaleFill(sourceRect.size, destinationRect);
|
||||
CGSize targetSize = SizeScaleByFactor(sourceRect.size, aspect);
|
||||
return RectAroundCenter(RectGetCenter(destinationRect), targetSize);
|
||||
}
|
||||
|
||||
CGRect RectInsetByPercent(CGRect rect, CGFloat percent)
|
||||
{
|
||||
CGFloat wInset = rect.size.width * (percent / 2.0f);
|
||||
CGFloat hInset = rect.size.height * (percent / 2.0f);
|
||||
return CGRectInset(rect, wInset, hInset);
|
||||
}
|
||||
|
||||
#pragma mark - Transforms
|
||||
|
||||
// Extract the x scale from transform
|
||||
CGFloat TransformGetXScale(CGAffineTransform t)
|
||||
{
|
||||
return sqrt(t.a * t.a + t.c * t.c);
|
||||
}
|
||||
|
||||
// Extract the y scale from transform
|
||||
CGFloat TransformGetYScale(CGAffineTransform t)
|
||||
{
|
||||
return sqrt(t.b * t.b + t.d * t.d);
|
||||
}
|
||||
|
||||
// Extract the rotation in radians
|
||||
CGFloat TransformGetRotation(CGAffineTransform t)
|
||||
{
|
||||
return atan2f(t.b, t.a);
|
||||
}
|
||||
Reference in New Issue
Block a user