refactor shape elements add responder system.

refactor shape elements add responder system.
Just iOS.
This commit is contained in:
Horcrux 2016-05-15 00:40:43 +08:00
Родитель 1f7a908406
Коммит 8d01e8eccb
65 изменённых файлов: 2354 добавлений и 213 удалений

Просмотреть файл

@ -570,6 +570,10 @@ npm install
3. Pattern element
4. Image element (Android)
5. calculate bounding box only if necessary.
6. miterLimit
7. move percentage convert and context bounding box to renderable
8. implement touchable elements ()
9. implement Animated elements
#### Thanks:

Просмотреть файл

@ -1,8 +1,13 @@
import {PropTypes} from 'react';
import Shape, {CIRCLE} from './Shape';
import React, {PropTypes, Component} from 'react';
import extractProps from '../lib/extract/extractProps';
import {RenderableAttributes} from '../lib/attributes';
import {requireNativeComponent} from 'react-native';
import mergeContext from '../lib/mergeContext';
import {circleProps, pathProps, fillProps, strokeProps} from '../lib/props';
import SvgTouchableMixin from '../lib/SvgTouchableMixin';
import _ from 'lodash';
class Circle extends Shape{
class Circle extends Component{
static displayName = 'Circle';
static propTypes = {
...pathProps,
@ -16,10 +21,34 @@ class Circle extends Shape{
isInGroup: PropTypes.bool
};
constructor() {
super(...arguments);
this.type = CIRCLE;
//constructor() {
// super(...arguments);
// _.forEach(SvgTouchableMixin, (method, key) => {
// this[key] = method.bind(this);
// });
//
// this.state = this.touchableGetInitialState();
//};
render() {
let props = mergeContext(this.props, this.context);
return <RNSVGCircle
{...extractProps(props)}
cx={props.cx.toString()}
cy={props.cy.toString()}
r={props.r.toString()}
//onStartShouldSetResponder={this.touchableHandleStartShouldSetResponder}
//onResponderTerminationRequest={this.touchableHandleResponderTerminationRequest}
//onResponderGrant={this.touchableHandleResponderGrant}
//onResponderMove={this.touchableHandleResponderMove}
//onResponderRelease={this.touchableHandleResponderRelease}
//onResponderTerminate={this.touchableHandleResponderTerminate}
/>;
}
}
const RNSVGCircle = requireNativeComponent('RNSVGCircle', null);
export default Circle;

Просмотреть файл

@ -1,8 +1,12 @@
import {PropTypes} from 'react';
import Shape, {ELLIPSE} from './Shape';
import React, {PropTypes, Component} from 'react';
import extractProps from '../lib/extract/extractProps';
import {RenderableAttributes} from '../lib/attributes';
import {requireNativeComponent} from 'react-native';
import mergeContext from '../lib/mergeContext';
import {ellipseProps, pathProps, fillProps, strokeProps} from '../lib/props';
class Ellipse extends Shape{
class Ellipse extends Component{
static displayName = 'Ellipse';
static propTypes = {
...pathProps,
@ -16,10 +20,17 @@ class Ellipse extends Shape{
isInGroup: PropTypes.bool
};
constructor() {
super(...arguments);
this.type = ELLIPSE;
render() {
let props = mergeContext(this.props, this.context);
return <RNSVGEllipse
{...extractProps(props)}
cx={props.cx.toString()}
cy={props.cy.toString()}
rx={props.rx.toString()}
ry={props.ry.toString()}
/>;
}
}
const RNSVGEllipse = requireNativeComponent('RNSVGEllipse', null);
export default Ellipse;

Просмотреть файл

@ -1,10 +1,10 @@
import React, {Component, PropTypes} from 'react';
import {requireNativeComponent} from 'react-native';
import extractProps from '../lib/extract/extractProps';
import {ImageAttributes} from '../lib/attributes';
import {numberProp} from '../lib/props';
import resolveAssetSource from 'react-native/Libraries/Image/resolveAssetSource';
import createReactNativeComponentClass from 'react-native/Libraries/ReactNative/createReactNativeComponentClass';
import formatPercentageProps from '../lib/formatPercentageProps';
class Image extends Component{
static displayName = 'Image';
@ -19,18 +19,18 @@ class Image extends Component{
render() {
let {props} = this;
return <RNSVGImage
{...extractProps(this.props, {transform: true})}
layout={formatPercentageProps(this.props, ['x', 'y', 'width', 'height'])}
src={resolveAssetSource(this.props.href)}
{...extractProps(props, {transform: true, responder: true})}
x={props.x.toString()}
y={props.y.toString()}
width={props.width.toString()}
height={props.height.toString()}
src={resolveAssetSource(props.href)}
/>;
}
}
let RNSVGImage = createReactNativeComponentClass({
validAttributes: ImageAttributes,
uiViewClassName: 'RNSVGImage'
});
const RNSVGImage = requireNativeComponent('RNSVGImage', null);
export default Image;

Просмотреть файл

@ -1,8 +1,11 @@
import {PropTypes} from 'react';
import Shape, {LINE} from './Shape';
import React, {PropTypes, Component} from 'react';
import extractProps from '../lib/extract/extractProps';
import {RenderableAttributes} from '../lib/attributes';
import {requireNativeComponent} from 'react-native';
import mergeContext from '../lib/mergeContext';
import {lineProps, pathProps, fillProps, strokeProps} from '../lib/props';
class Line extends Shape{
class Line extends Component{
static displayName = 'Line';
static propTypes = {
...pathProps,
@ -16,10 +19,17 @@ class Line extends Shape{
isInGroup: PropTypes.bool
};
constructor() {
super(...arguments);
this.type = LINE;
render() {
let props = mergeContext(this.props, this.context);
return <RNSVGLine
{...extractProps(props)}
x1={props.x1.toString()}
y1={props.y1.toString()}
x2={props.x2.toString()}
y2={props.y2.toString()}
/>;
}
}
const RNSVGLine = requireNativeComponent('RNSVGLine', null);
export default Line;

Просмотреть файл

@ -1,8 +1,12 @@
import {PropTypes} from 'react';
import Shape, {RECT} from './Shape';
import React, {PropTypes, Component} from 'react';
import './Path'; // must import Path first, don`t know why. without this will throw an `Super expression must either be null or a function, not undefined`
import extractProps from '../lib/extract/extractProps';
import {RenderableAttributes} from '../lib/attributes';
import {requireNativeComponent} from 'react-native';
import mergeContext from '../lib/mergeContext';
import {rectProps, pathProps, fillProps, strokeProps} from '../lib/props';
class Rect extends Shape{
class Rect extends Component{
static displayName = 'Rect';
static propTypes = {
...pathProps,
@ -16,10 +20,25 @@ class Rect extends Shape{
isInGroup: PropTypes.bool
};
constructor() {
super(...arguments);
this.type = RECT;
render() {
let props = mergeContext(this.props, this.context);
return <RNSVGRect
{...extractProps({
...props,
x: null,
y: null
})}
x={props.x.toString()}
y={props.y.toString()}
width={props.width.toString()}
height={props.height.toString()}
rx={props.rx ? props.rx.toString() : '0'}
ry={props.ry ? props.ry.toString() : '0'}
/>;
}
}
const RNSVGRect = requireNativeComponent('RNSVGRect', null);
export default Rect;

Просмотреть файл

@ -67,6 +67,12 @@ class Svg extends Component{
return (
<NativeSvgView
{...props}
opacity={null}
width={null}
height={null}
viewbox={null}
preserveAspectRatio={null}
ref={ele => this.root = ele}
style={[
props.style,
@ -86,6 +92,6 @@ class Svg extends Component{
}
}
const NativeSvgView = requireNativeComponent('RNSVGSvgView', Svg);
const NativeSvgView = requireNativeComponent('RNSVGSvgView', null);
export default Svg;

Просмотреть файл

@ -1,7 +1,7 @@
import React, {Component, PropTypes} from 'react';
import {requireNativeComponent} from 'react-native';
import Defs from './Defs';
import _ from 'lodash';
import createReactNativeComponentClass from 'react-native/Libraries/ReactNative/createReactNativeComponentClass';
import extractProps from '../lib/extract/extractProps';
import extractText from '../lib/extract/extractText';
import {TextAttributes} from '../lib/attributes';
@ -53,9 +53,9 @@ class Text extends Component{
<Text {...this.props} id={null} />
</Defs.Item>;
}
// TODO: support percent gradients
return (
<NativeText
<RNSVGText
{...extractProps({...props, x, y})}
{...extractText(props)}
/>
@ -63,9 +63,8 @@ class Text extends Component{
}
}
let NativeText = createReactNativeComponentClass({
validAttributes: TextAttributes,
uiViewClassName: 'RNSVGText'
const RNSVGText = requireNativeComponent('RNSVGText', null, {
nativeOnly: TextAttributes
});
export default Text;

Просмотреть файл

@ -8,6 +8,7 @@
#import <CoreGraphics/CoreGraphics.h>
#import <Foundation/Foundation.h>
#import "RNSVGPercentageConverter.h"
@interface RNSVGBrush : NSObject
{
@ -29,8 +30,6 @@
- (BOOL)applyStrokeColor:(CGContextRef)context;
- (CGFloat)getActualProp:(int)percent relative:(CGFloat)relative offset:(CGFloat)offset;
/**
* paint fills the context with a brush. The context is assumed to
* be clipped.

Просмотреть файл

@ -29,30 +29,6 @@ RCT_NOT_IMPLEMENTED(- (instancetype)init)
return NO;
}
- (CGFloat)getActualProp:(int)index relative:(CGFloat)relative offset:(CGFloat)offset
{
id coord = [_points objectAtIndex:index];
if ([coord isKindOfClass:[NSString class]]) {
__block float matched = [coord floatValue];
NSString *percentage = (NSString *)coord;
NSRegularExpression *regex = [[NSRegularExpression alloc] initWithPattern:@"^(\\-?\\d+(?:\\.\\d+)?)%$" options:0 error:NULL];
[regex enumerateMatchesInString:percentage
options:0
range:NSMakeRange(0, percentage.length)
usingBlock:^(NSTextCheckingResult *result, NSMatchingFlags flags, BOOL *stop)
{
matched = [[percentage substringWithRange:NSMakeRange(result.range.location, result.range.length)] floatValue];
matched = matched / 100 * relative + offset;
}];
return matched;
} else {
return [coord floatValue];
}
}
- (void)paint:(CGContextRef)context
{
// abstract

Просмотреть файл

@ -49,10 +49,11 @@
float offsetX = (midX - width / 2);
float offsetY = (midY - height / 2);
CGFloat x1 = [self getActualProp:0 relative:width offset:offsetX];
CGFloat y1 = [self getActualProp:1 relative:height offset:offsetY];
CGFloat x2 = [self getActualProp:2 relative:width offset:offsetX];
CGFloat y2 = [self getActualProp:3 relative:height offset:offsetY];
RNSVGPercentageConverter* convert = [[RNSVGPercentageConverter alloc] init];
CGFloat x1 = [convert stringToFloat:(NSString *)[_points objectAtIndex:0] relative:width offset:offsetX];
CGFloat y1 = [convert stringToFloat:(NSString *)[_points objectAtIndex:1] relative:height offset:offsetY];
CGFloat x2 = [convert stringToFloat:(NSString *)[_points objectAtIndex:2] relative:width offset:offsetX];
CGFloat y2 = [convert stringToFloat:(NSString *)[_points objectAtIndex:3] relative:height offset:offsetY];
CGContextDrawLinearGradient(context, _gradient, CGPointMake(x1, y1), CGPointMake(x2, y2), extendOptions);
}

Просмотреть файл

@ -9,6 +9,7 @@
#import "RNSVGRadialGradient.h"
#import "RCTConvert+RNSVG.h"
#import "RNSVGNode.h"
#import "RCTLog.h"
@implementation RNSVGRadialGradient
@ -60,12 +61,15 @@
float midY = CGRectGetMidY(box);
float offsetX = (midX - width / 2);
float offsetY = (midY - height / 2);
CGFloat rx = [self getActualProp:2 relative:width offset:0];
CGFloat ry = [self getActualProp:3 relative:height offset:0];
CGFloat fx = [self getActualProp:0 relative:width offset:offsetX];
CGFloat fy = [self getActualProp:1 relative:height offset:offsetY] / (ry / rx);
CGFloat cx = [self getActualProp:4 relative:width offset:offsetX];
CGFloat cy = [self getActualProp:5 relative:height offset:offsetY] / (ry / rx);
RNSVGPercentageConverter* convert = [[RNSVGPercentageConverter alloc] init];
CGFloat rx = [convert stringToFloat:(NSString *)[_points objectAtIndex:2] relative:width offset:0];
CGFloat ry = [convert stringToFloat:(NSString *)[_points objectAtIndex:3] relative:height offset:0];
CGFloat fx = [convert stringToFloat:(NSString *)[_points objectAtIndex:0] relative:width offset:offsetX];
CGFloat fy = [convert stringToFloat:(NSString *)[_points objectAtIndex:1] relative:height offset:offsetY] / (ry / rx);
CGFloat cx = [convert stringToFloat:(NSString *)[_points objectAtIndex:4] relative:width offset:offsetX];
CGFloat cy = [convert stringToFloat:(NSString *)[_points objectAtIndex:5] relative:height offset:offsetY] / (ry / rx);
CGAffineTransform transform = CGAffineTransformMakeScale(1, ry / rx);
CGContextConcatCTM(context, transform);

19
ios/Elements/RNSVGGroup.h Normal file
Просмотреть файл

@ -0,0 +1,19 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <Foundation/Foundation.h>
#import "RNSVGContainer.h"
#import "RNSVGNode.h"
#import "RNSVGCGFCRule.h"
@interface RNSVGGroup : RNSVGNode <RNSVGContainer>
@property (nonatomic, strong) NSString *asClipPath; // Current group is a <ClipPath /> element and asClipPath is its id.
@end

36
ios/Elements/RNSVGGroup.m Normal file
Просмотреть файл

@ -0,0 +1,36 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGGroup.h"
@implementation RNSVGGroup
- (void)renderLayerTo:(CGContextRef)context
{
if (self.asClipPath == NULL) {
[self clip:context];
for (RNSVGNode *node in self.subviews) {
[node renderTo:context];
}
} else {
[self defineClipPath:[self getPath:context] clipPathId:self.asClipPath];
}
}
- (CGPathRef)getPath:(CGContextRef)context
{
CGMutablePathRef path = CGPathCreateMutable();
for (RNSVGNode *node in self.subviews) {
CGAffineTransform transform = node.transform;
CGPathAddPath(path, &transform, [node getPath:context]);
}
return path;
}
@end

20
ios/Elements/RNSVGImage.h Normal file
Просмотреть файл

@ -0,0 +1,20 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <Foundation/Foundation.h>
#import "RNSVGRenderable.h"
@interface RNSVGImage : RNSVGRenderable
@property (nonatomic, assign) id src;
@property (nonatomic, strong) NSString* x;
@property (nonatomic, strong) NSString* y;
@property (nonatomic, strong) NSString* width;
@property (nonatomic, strong) NSString* height;
@end

93
ios/Elements/RNSVGImage.m Normal file
Просмотреть файл

@ -0,0 +1,93 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGImage.h"
#import "RCTConvert+RNSVG.h"
#import "RCTLog.h"
@implementation RNSVGImage
{
CGImageRef image;
}
- (void)setSrc:(id)src
{
if (src == _src) {
return;
}
_src = src;
CGImageRelease(image);
image = CGImageRetain([RCTConvert CGImage:src]);
[self invalidate];
}
- (void)setX:(NSString *)x
{
if (x == _x) {
return;
}
[self invalidate];
_x = x;
}
- (void)setY:(NSString *)y
{
if (y == _y) {
return;
}
[self invalidate];
_y = y;
}
- (void)setWidth:(NSString *)width
{
if (width == _width) {
return;
}
[self invalidate];
_width = width;
}
- (void)setHeight:(NSString *)height
{
if (height == _height) {
return;
}
[self invalidate];
_height = height;
}
- (void)dealloc
{
CGImageRelease(image);
}
- (void)renderLayerTo:(CGContextRef)context
{
CGRect box = CGContextGetClipBoundingBox(context);
float height = CGRectGetHeight(box);
float width = CGRectGetWidth(box);
RNSVGPercentageConverter* convert = [[RNSVGPercentageConverter alloc] init];
CGFloat x = [convert stringToFloat:self.x relative:width offset:0];
CGFloat y = [convert stringToFloat:self.y relative:height offset:0];
CGFloat w = [convert stringToFloat:self.width relative:width offset:0];
CGFloat h = [convert stringToFloat:self.height relative:height offset:0];
// add hit area
CGPathAddPath(self.nodeArea, nil, CGPathCreateWithRect(CGRectMake(x, y, w, h), nil));
[self clip:context];
CGContextSaveGState(context);
CGContextTranslateCTM(context, 0, h);
CGContextScaleCTM(context, 1.0, -1.0);
CGContextDrawImage(context, CGRectMake(x, -y, w, h), image);
CGContextRestoreGState(context);
}
@end

17
ios/Elements/RNSVGPath.h Normal file
Просмотреть файл

@ -0,0 +1,17 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <Foundation/Foundation.h>
#import "RNSVGRenderable.h"
@interface RNSVGPath : RNSVGRenderable
@property (nonatomic, assign) CGPathRef d;
@end

109
ios/Elements/RNSVGPath.m Normal file
Просмотреть файл

@ -0,0 +1,109 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGPath.h"
@implementation RNSVGPath
- (void)setD:(CGPathRef)d
{
if (d == _d) {
return;
}
[self invalidate];
CGPathRelease(_d);
_d = CGPathRetain(d);
}
- (void)dealloc
{
CGPathRelease(_d);
}
- (void)renderLayerTo:(CGContextRef)context
{
if ((!self.fill && !self.stroke) || !self.d) {
return;
}
CGPathDrawingMode mode = kCGPathStroke;
BOOL fillColor = YES;
// Add path to nodeArea
CGPathAddPath(self.nodeArea, nil, _d);
if (self.fill) {
mode = self.fillRule == kRNSVGCGFCRuleEvenodd ? kCGPathEOFill : kCGPathFill;
fillColor = [self.fill applyFillColor:context];
if (!fillColor) {
[self clip:context];
CGContextSaveGState(context);
CGContextAddPath(context, self.d);
CGContextClip(context);
[self.fill paint:context];
CGContextRestoreGState(context);
if (!self.stroke) {
return;
}
}
}
if (self.stroke) {
// Add stroke to nodeArea
CGPathRef strokePath = CGPathCreateCopyByStrokingPath(_d, nil, self.strokeWidth, self.strokeLinecap, self.strokeLinejoin, 0);
CGPathAddPath(self.nodeArea, nil, strokePath);
CGContextSetLineWidth(context, self.strokeWidth);
CGContextSetLineCap(context, self.strokeLinecap);
CGContextSetLineJoin(context, self.strokeLinejoin);
RNSVGCGFloatArray dash = self.strokeDasharray;
if (dash.count) {
CGContextSetLineDash(context, self.strokeDashoffset, dash.array, dash.count);
}
if (!fillColor) {
CGContextAddPath(context, self.d);
CGContextReplacePathWithStrokedPath(context);
CGContextClip(context);
}
if ([self.stroke applyStrokeColor:context]) {
if (mode == kCGPathFill) {
mode = kCGPathFillStroke;
} else if (mode == kCGPathEOFill) {
mode = kCGPathEOFillStroke;
}
} else {
// draw fill
[self clip:context];
CGContextAddPath(context, self.d);
CGContextDrawPath(context, mode);
// draw stroke
CGContextAddPath(context, self.d);
CGContextReplacePathWithStrokedPath(context);
CGContextClip(context);
[self.stroke paint:context];
return;
}
}
[self clip:context];
CGContextAddPath(context, self.d);
CGContextDrawPath(context, mode);
}
- (CGPathRef)getPath:(CGContextRef)context
{
return self.d;
}
@end

Просмотреть файл

@ -0,0 +1,14 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <UIKit/UIKit.h>
#import "RNSVGContainer.h"
@interface RNSVGSvgView : UIView <RNSVGContainer>
@end

Просмотреть файл

@ -0,0 +1,34 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGSvgView.h"
#import "RNSVGNode.h"
#import "RCTLog.h"
@implementation RNSVGSvgView
- (void)invalidate
{
[self setNeedsDisplay];
}
- (void)drawRect:(CGRect)rect
{
CGContextRef context = UIGraphicsGetCurrentContext();
for (RNSVGNode *node in self.subviews) {
[node renderTo:context];
}
}
- (void)reactSetInheritedBackgroundColor:(UIColor *)inheritedBackgroundColor
{
self.backgroundColor = inheritedBackgroundColor;
}
@end

Просмотреть файл

@ -7,30 +7,37 @@
objects = {
/* Begin PBXBuildFile section */
0CF68B051AF0549300FF9E5C /* RNSVGGroup.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68ADE1AF0549300FF9E5C /* RNSVGGroup.m */; };
0CF68B061AF0549300FF9E5C /* RNSVGNode.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68AE01AF0549300FF9E5C /* RNSVGNode.m */; };
0CF68B071AF0549300FF9E5C /* RNSVGRenderable.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68AE21AF0549300FF9E5C /* RNSVGRenderable.m */; };
0CF68B0A1AF0549300FF9E5C /* RNSVGText.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68AE81AF0549300FF9E5C /* RNSVGText.m */; };
0CF68B0B1AF0549300FF9E5C /* RNSVGBrush.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68AEC1AF0549300FF9E5C /* RNSVGBrush.m */; };
0CF68B0C1AF0549300FF9E5C /* RNSVGLinearGradient.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68AEE1AF0549300FF9E5C /* RNSVGLinearGradient.m */; };
0CF68B0D1AF0549300FF9E5C /* RNSVGPattern.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68AF01AF0549300FF9E5C /* RNSVGPattern.m */; };
0CF68B0E1AF0549300FF9E5C /* RNSVGRadialGradient.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68AF21AF0549300FF9E5C /* RNSVGRadialGradient.m */; };
0CF68B0F1AF0549300FF9E5C /* RNSVGSolidColor.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68AF41AF0549300FF9E5C /* RNSVGSolidColor.m */; };
0CF68B101AF0549300FF9E5C /* RCTConvert+RNSVG.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68AF71AF0549300FF9E5C /* RCTConvert+RNSVG.m */; };
0CF68B111AF0549300FF9E5C /* RNSVGGroupManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68AFA1AF0549300FF9E5C /* RNSVGGroupManager.m */; };
0CF68B121AF0549300FF9E5C /* RNSVGNodeManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68AFC1AF0549300FF9E5C /* RNSVGNodeManager.m */; };
0CF68B131AF0549300FF9E5C /* RNSVGRenderableManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68AFE1AF0549300FF9E5C /* RNSVGRenderableManager.m */; };
0CF68B161AF0549300FF9E5C /* RNSVGTextManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 0CF68B041AF0549300FF9E5C /* RNSVGTextManager.m */; };
108FD88C1CDAF09B00A65FB3 /* RNSVGImageManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 108FD88B1CDAF09B00A65FB3 /* RNSVGImageManager.m */; };
108FD88F1CDAF0A300A65FB3 /* RNSVGImage.m in Sources */ = {isa = PBXBuildFile; fileRef = 108FD88E1CDAF0A300A65FB3 /* RNSVGImage.m */; };
10A062FE1CC732020000CEEF /* RNSVGPathManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10A062FB1CC732020000CEEF /* RNSVGPathManager.m */; };
10A062FF1CC732020000CEEF /* RNSVGSvgViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10A062FD1CC732020000CEEF /* RNSVGSvgViewManager.m */; };
10A063041CC7320C0000CEEF /* RNSVGPath.m in Sources */ = {isa = PBXBuildFile; fileRef = 10A063011CC7320C0000CEEF /* RNSVGPath.m */; };
10A063051CC7320C0000CEEF /* RNSVGSvgView.m in Sources */ = {isa = PBXBuildFile; fileRef = 10A063031CC7320C0000CEEF /* RNSVGSvgView.m */; };
10B898DF1CE45973003CD3D4 /* RNSVGGlyphCache.m in Sources */ = {isa = PBXBuildFile; fileRef = 10B898DE1CE45973003CD3D4 /* RNSVGGlyphCache.m */; };
10B898E11CE490FC003CD3D4 /* UIBezierPath-Points.m in Sources */ = {isa = PBXBuildFile; fileRef = 10B898E01CE490FC003CD3D4 /* UIBezierPath-Points.m */; };
10C068671CCF0F87007C6982 /* RNSVGShape.m in Sources */ = {isa = PBXBuildFile; fileRef = 10C068651CCF0F87007C6982 /* RNSVGShape.m */; };
10C0686A1CCF1061007C6982 /* RNSVGShapeManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10C068691CCF1061007C6982 /* RNSVGShapeManager.m */; };
1039D2891CE71EB7001E90A8 /* RNSVGGroup.m in Sources */ = {isa = PBXBuildFile; fileRef = 1039D2821CE71EB7001E90A8 /* RNSVGGroup.m */; };
1039D28A1CE71EB7001E90A8 /* RNSVGImage.m in Sources */ = {isa = PBXBuildFile; fileRef = 1039D2841CE71EB7001E90A8 /* RNSVGImage.m */; };
1039D28B1CE71EB7001E90A8 /* RNSVGPath.m in Sources */ = {isa = PBXBuildFile; fileRef = 1039D2861CE71EB7001E90A8 /* RNSVGPath.m */; };
1039D28C1CE71EB7001E90A8 /* RNSVGSvgView.m in Sources */ = {isa = PBXBuildFile; fileRef = 1039D2881CE71EB7001E90A8 /* RNSVGSvgView.m */; };
1039D2941CE71EC2001E90A8 /* RnSVGGlyphCache.m in Sources */ = {isa = PBXBuildFile; fileRef = 1039D28E1CE71EC2001E90A8 /* RnSVGGlyphCache.m */; };
1039D2951CE71EC2001E90A8 /* RNSVGText.m in Sources */ = {isa = PBXBuildFile; fileRef = 1039D2901CE71EC2001E90A8 /* RNSVGText.m */; };
1039D2961CE71EC2001E90A8 /* UIBezierPath-Points.m in Sources */ = {isa = PBXBuildFile; fileRef = 1039D2931CE71EC2001E90A8 /* UIBezierPath-Points.m */; };
1039D2A01CE72177001E90A8 /* RCTConvert+RNSVG.m in Sources */ = {isa = PBXBuildFile; fileRef = 1039D29C1CE72177001E90A8 /* RCTConvert+RNSVG.m */; };
1039D2B01CE72F27001E90A8 /* RNSVGPercentageConverter.m in Sources */ = {isa = PBXBuildFile; fileRef = 1039D2AF1CE72F27001E90A8 /* RNSVGPercentageConverter.m */; };
10BA0D341CE74E3100887C2B /* RNSVGCircleManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D1D1CE74E3100887C2B /* RNSVGCircleManager.m */; };
10BA0D351CE74E3100887C2B /* RNSVGEllipseManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D1F1CE74E3100887C2B /* RNSVGEllipseManager.m */; };
10BA0D361CE74E3100887C2B /* RNSVGGroupManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D211CE74E3100887C2B /* RNSVGGroupManager.m */; };
10BA0D371CE74E3100887C2B /* RNSVGImageManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D231CE74E3100887C2B /* RNSVGImageManager.m */; };
10BA0D381CE74E3100887C2B /* RNSVGLineManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D251CE74E3100887C2B /* RNSVGLineManager.m */; };
10BA0D391CE74E3100887C2B /* RNSVGNodeManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D271CE74E3100887C2B /* RNSVGNodeManager.m */; };
10BA0D3A1CE74E3100887C2B /* RNSVGPathManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D291CE74E3100887C2B /* RNSVGPathManager.m */; };
10BA0D3B1CE74E3100887C2B /* RNSVGRectManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D2B1CE74E3100887C2B /* RNSVGRectManager.m */; };
10BA0D3C1CE74E3100887C2B /* RNSVGRenderableManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D2D1CE74E3100887C2B /* RNSVGRenderableManager.m */; };
10BA0D3E1CE74E3100887C2B /* RNSVGSvgViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D311CE74E3100887C2B /* RNSVGSvgViewManager.m */; };
10BA0D3F1CE74E3100887C2B /* RNSVGTextManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D331CE74E3100887C2B /* RNSVGTextManager.m */; };
10BA0D481CE74E3D00887C2B /* RNSVGCircle.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D411CE74E3D00887C2B /* RNSVGCircle.m */; };
10BA0D491CE74E3D00887C2B /* RNSVGEllipse.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D431CE74E3D00887C2B /* RNSVGEllipse.m */; };
10BA0D4A1CE74E3D00887C2B /* RNSVGLine.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D451CE74E3D00887C2B /* RNSVGLine.m */; };
10BA0D4B1CE74E3D00887C2B /* RNSVGRect.m in Sources */ = {isa = PBXBuildFile; fileRef = 10BA0D471CE74E3D00887C2B /* RNSVGRect.m */; };
/* End PBXBuildFile section */
/* Begin PBXCopyFilesBuildPhase section */
@ -47,17 +54,10 @@
/* Begin PBXFileReference section */
0CF68AC11AF0540F00FF9E5C /* libRNSVG.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = libRNSVG.a; sourceTree = BUILT_PRODUCTS_DIR; };
0CF68ADB1AF0549300FF9E5C /* RNSVGCGFloatArray.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGCGFloatArray.h; sourceTree = "<group>"; };
0CF68ADC1AF0549300FF9E5C /* RNSVGContainer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGContainer.h; sourceTree = "<group>"; };
0CF68ADD1AF0549300FF9E5C /* RNSVGGroup.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGGroup.h; sourceTree = "<group>"; };
0CF68ADE1AF0549300FF9E5C /* RNSVGGroup.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGGroup.m; sourceTree = "<group>"; };
0CF68ADF1AF0549300FF9E5C /* RNSVGNode.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGNode.h; sourceTree = "<group>"; };
0CF68AE01AF0549300FF9E5C /* RNSVGNode.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGNode.m; sourceTree = "<group>"; };
0CF68AE11AF0549300FF9E5C /* RNSVGRenderable.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGRenderable.h; sourceTree = "<group>"; };
0CF68AE21AF0549300FF9E5C /* RNSVGRenderable.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGRenderable.m; sourceTree = "<group>"; };
0CF68AE71AF0549300FF9E5C /* RNSVGText.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGText.h; sourceTree = "<group>"; };
0CF68AE81AF0549300FF9E5C /* RNSVGText.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGText.m; sourceTree = "<group>"; };
0CF68AE91AF0549300FF9E5C /* RNSVGTextFrame.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGTextFrame.h; sourceTree = "<group>"; };
0CF68AEB1AF0549300FF9E5C /* RNSVGBrush.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGBrush.h; sourceTree = "<group>"; };
0CF68AEC1AF0549300FF9E5C /* RNSVGBrush.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGBrush.m; sourceTree = "<group>"; };
0CF68AED1AF0549300FF9E5C /* RNSVGLinearGradient.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGLinearGradient.h; sourceTree = "<group>"; };
@ -68,37 +68,58 @@
0CF68AF21AF0549300FF9E5C /* RNSVGRadialGradient.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGRadialGradient.m; sourceTree = "<group>"; };
0CF68AF31AF0549300FF9E5C /* RNSVGSolidColor.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGSolidColor.h; sourceTree = "<group>"; };
0CF68AF41AF0549300FF9E5C /* RNSVGSolidColor.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGSolidColor.m; sourceTree = "<group>"; };
0CF68AF61AF0549300FF9E5C /* RCTConvert+RNSVG.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "RCTConvert+RNSVG.h"; sourceTree = "<group>"; };
0CF68AF71AF0549300FF9E5C /* RCTConvert+RNSVG.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "RCTConvert+RNSVG.m"; sourceTree = "<group>"; };
0CF68AF91AF0549300FF9E5C /* RNSVGGroupManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGGroupManager.h; sourceTree = "<group>"; };
0CF68AFA1AF0549300FF9E5C /* RNSVGGroupManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGGroupManager.m; sourceTree = "<group>"; };
0CF68AFB1AF0549300FF9E5C /* RNSVGNodeManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGNodeManager.h; sourceTree = "<group>"; };
0CF68AFC1AF0549300FF9E5C /* RNSVGNodeManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGNodeManager.m; sourceTree = "<group>"; };
0CF68AFD1AF0549300FF9E5C /* RNSVGRenderableManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGRenderableManager.h; sourceTree = "<group>"; };
0CF68AFE1AF0549300FF9E5C /* RNSVGRenderableManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGRenderableManager.m; sourceTree = "<group>"; };
0CF68B031AF0549300FF9E5C /* RNSVGTextManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGTextManager.h; sourceTree = "<group>"; };
0CF68B041AF0549300FF9E5C /* RNSVGTextManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGTextManager.m; sourceTree = "<group>"; };
108FD88A1CDAF09B00A65FB3 /* RNSVGImageManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGImageManager.h; sourceTree = "<group>"; };
108FD88B1CDAF09B00A65FB3 /* RNSVGImageManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGImageManager.m; sourceTree = "<group>"; };
108FD88D1CDAF0A300A65FB3 /* RNSVGImage.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGImage.h; sourceTree = "<group>"; };
108FD88E1CDAF0A300A65FB3 /* RNSVGImage.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGImage.m; sourceTree = "<group>"; };
10A062FA1CC732020000CEEF /* RNSVGPathManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGPathManager.h; sourceTree = "<group>"; };
10A062FB1CC732020000CEEF /* RNSVGPathManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGPathManager.m; sourceTree = "<group>"; };
10A062FC1CC732020000CEEF /* RNSVGSvgViewManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGSvgViewManager.h; sourceTree = "<group>"; };
10A062FD1CC732020000CEEF /* RNSVGSvgViewManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGSvgViewManager.m; sourceTree = "<group>"; };
10A063001CC7320C0000CEEF /* RNSVGPath.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGPath.h; sourceTree = "<group>"; };
10A063011CC7320C0000CEEF /* RNSVGPath.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGPath.m; sourceTree = "<group>"; };
10A063021CC7320C0000CEEF /* RNSVGSvgView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGSvgView.h; sourceTree = "<group>"; };
10A063031CC7320C0000CEEF /* RNSVGSvgView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGSvgView.m; sourceTree = "<group>"; };
10B898DD1CE4591F003CD3D4 /* RNSVGGlyphCache.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGGlyphCache.h; sourceTree = "<group>"; };
10B898DE1CE45973003CD3D4 /* RNSVGGlyphCache.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGGlyphCache.m; sourceTree = "<group>"; };
10B898E01CE490FC003CD3D4 /* UIBezierPath-Points.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "UIBezierPath-Points.m"; sourceTree = "<group>"; };
10B898E21CE4910A003CD3D4 /* UIBezierPath-Points.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "UIBezierPath-Points.h"; sourceTree = "<group>"; };
10C068641CCF0F87007C6982 /* RNSVGShape.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGShape.h; sourceTree = SOURCE_ROOT; };
10C068651CCF0F87007C6982 /* RNSVGShape.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGShape.m; sourceTree = SOURCE_ROOT; };
10C068681CCF1061007C6982 /* RNSVGShapeManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGShapeManager.h; sourceTree = "<group>"; };
10C068691CCF1061007C6982 /* RNSVGShapeManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGShapeManager.m; sourceTree = "<group>"; };
10FEAC6A1CC7D05200F1C23C /* RNSVGCGFCRule.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGCGFCRule.h; sourceTree = "<group>"; };
1039D2811CE71EB7001E90A8 /* RNSVGGroup.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGGroup.h; path = Elements/RNSVGGroup.h; sourceTree = "<group>"; };
1039D2821CE71EB7001E90A8 /* RNSVGGroup.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = RNSVGGroup.m; path = Elements/RNSVGGroup.m; sourceTree = "<group>"; };
1039D2831CE71EB7001E90A8 /* RNSVGImage.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGImage.h; path = Elements/RNSVGImage.h; sourceTree = "<group>"; };
1039D2841CE71EB7001E90A8 /* RNSVGImage.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = RNSVGImage.m; path = Elements/RNSVGImage.m; sourceTree = "<group>"; };
1039D2851CE71EB7001E90A8 /* RNSVGPath.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGPath.h; path = Elements/RNSVGPath.h; sourceTree = "<group>"; };
1039D2861CE71EB7001E90A8 /* RNSVGPath.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = RNSVGPath.m; path = Elements/RNSVGPath.m; sourceTree = "<group>"; };
1039D2871CE71EB7001E90A8 /* RNSVGSvgView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGSvgView.h; path = Elements/RNSVGSvgView.h; sourceTree = "<group>"; };
1039D2881CE71EB7001E90A8 /* RNSVGSvgView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = RNSVGSvgView.m; path = Elements/RNSVGSvgView.m; sourceTree = "<group>"; };
1039D28D1CE71EC2001E90A8 /* RNSVGGlyphCache.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGGlyphCache.h; path = Text/RNSVGGlyphCache.h; sourceTree = "<group>"; };
1039D28E1CE71EC2001E90A8 /* RnSVGGlyphCache.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = RnSVGGlyphCache.m; path = Text/RnSVGGlyphCache.m; sourceTree = "<group>"; };
1039D28F1CE71EC2001E90A8 /* RNSVGText.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGText.h; path = Text/RNSVGText.h; sourceTree = "<group>"; };
1039D2901CE71EC2001E90A8 /* RNSVGText.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = RNSVGText.m; path = Text/RNSVGText.m; sourceTree = "<group>"; };
1039D2911CE71EC2001E90A8 /* RNSVGTextFrame.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGTextFrame.h; path = Text/RNSVGTextFrame.h; sourceTree = "<group>"; };
1039D2921CE71EC2001E90A8 /* UIBezierPath-Points.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = "UIBezierPath-Points.h"; path = "Text/UIBezierPath-Points.h"; sourceTree = "<group>"; };
1039D2931CE71EC2001E90A8 /* UIBezierPath-Points.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = "UIBezierPath-Points.m"; path = "Text/UIBezierPath-Points.m"; sourceTree = "<group>"; };
1039D29B1CE72177001E90A8 /* RCTConvert+RNSVG.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = "RCTConvert+RNSVG.h"; path = "Utils/RCTConvert+RNSVG.h"; sourceTree = "<group>"; };
1039D29C1CE72177001E90A8 /* RCTConvert+RNSVG.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = "RCTConvert+RNSVG.m"; path = "Utils/RCTConvert+RNSVG.m"; sourceTree = "<group>"; };
1039D29D1CE72177001E90A8 /* RNSVGCGFCRule.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGCGFCRule.h; path = Utils/RNSVGCGFCRule.h; sourceTree = "<group>"; };
1039D29E1CE72177001E90A8 /* RNSVGCGFloatArray.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGCGFloatArray.h; path = Utils/RNSVGCGFloatArray.h; sourceTree = "<group>"; };
1039D2A11CE721A7001E90A8 /* RNSVGContainer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGContainer.h; sourceTree = "<group>"; };
1039D2AE1CE72F27001E90A8 /* RNSVGPercentageConverter.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGPercentageConverter.h; path = Utils/RNSVGPercentageConverter.h; sourceTree = "<group>"; };
1039D2AF1CE72F27001E90A8 /* RNSVGPercentageConverter.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = RNSVGPercentageConverter.m; path = Utils/RNSVGPercentageConverter.m; sourceTree = "<group>"; };
10BA0D1C1CE74E3100887C2B /* RNSVGCircleManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGCircleManager.h; sourceTree = "<group>"; };
10BA0D1D1CE74E3100887C2B /* RNSVGCircleManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGCircleManager.m; sourceTree = "<group>"; };
10BA0D1E1CE74E3100887C2B /* RNSVGEllipseManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGEllipseManager.h; sourceTree = "<group>"; };
10BA0D1F1CE74E3100887C2B /* RNSVGEllipseManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGEllipseManager.m; sourceTree = "<group>"; };
10BA0D201CE74E3100887C2B /* RNSVGGroupManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGGroupManager.h; sourceTree = "<group>"; };
10BA0D211CE74E3100887C2B /* RNSVGGroupManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGGroupManager.m; sourceTree = "<group>"; };
10BA0D221CE74E3100887C2B /* RNSVGImageManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGImageManager.h; sourceTree = "<group>"; };
10BA0D231CE74E3100887C2B /* RNSVGImageManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGImageManager.m; sourceTree = "<group>"; };
10BA0D241CE74E3100887C2B /* RNSVGLineManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGLineManager.h; sourceTree = "<group>"; };
10BA0D251CE74E3100887C2B /* RNSVGLineManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGLineManager.m; sourceTree = "<group>"; };
10BA0D261CE74E3100887C2B /* RNSVGNodeManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGNodeManager.h; sourceTree = "<group>"; };
10BA0D271CE74E3100887C2B /* RNSVGNodeManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGNodeManager.m; sourceTree = "<group>"; };
10BA0D281CE74E3100887C2B /* RNSVGPathManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGPathManager.h; sourceTree = "<group>"; };
10BA0D291CE74E3100887C2B /* RNSVGPathManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGPathManager.m; sourceTree = "<group>"; };
10BA0D2A1CE74E3100887C2B /* RNSVGRectManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGRectManager.h; sourceTree = "<group>"; };
10BA0D2B1CE74E3100887C2B /* RNSVGRectManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGRectManager.m; sourceTree = "<group>"; };
10BA0D2C1CE74E3100887C2B /* RNSVGRenderableManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGRenderableManager.h; sourceTree = "<group>"; };
10BA0D2D1CE74E3100887C2B /* RNSVGRenderableManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGRenderableManager.m; sourceTree = "<group>"; };
10BA0D301CE74E3100887C2B /* RNSVGSvgViewManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGSvgViewManager.h; sourceTree = "<group>"; };
10BA0D311CE74E3100887C2B /* RNSVGSvgViewManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGSvgViewManager.m; sourceTree = "<group>"; };
10BA0D321CE74E3100887C2B /* RNSVGTextManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RNSVGTextManager.h; sourceTree = "<group>"; };
10BA0D331CE74E3100887C2B /* RNSVGTextManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RNSVGTextManager.m; sourceTree = "<group>"; };
10BA0D401CE74E3D00887C2B /* RNSVGCircle.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGCircle.h; path = Shapes/RNSVGCircle.h; sourceTree = "<group>"; };
10BA0D411CE74E3D00887C2B /* RNSVGCircle.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = RNSVGCircle.m; path = Shapes/RNSVGCircle.m; sourceTree = "<group>"; };
10BA0D421CE74E3D00887C2B /* RNSVGEllipse.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGEllipse.h; path = Shapes/RNSVGEllipse.h; sourceTree = "<group>"; };
10BA0D431CE74E3D00887C2B /* RNSVGEllipse.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = RNSVGEllipse.m; path = Shapes/RNSVGEllipse.m; sourceTree = "<group>"; };
10BA0D441CE74E3D00887C2B /* RNSVGLine.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGLine.h; path = Shapes/RNSVGLine.h; sourceTree = "<group>"; };
10BA0D451CE74E3D00887C2B /* RNSVGLine.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = RNSVGLine.m; path = Shapes/RNSVGLine.m; sourceTree = "<group>"; };
10BA0D461CE74E3D00887C2B /* RNSVGRect.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RNSVGRect.h; path = Shapes/RNSVGRect.h; sourceTree = "<group>"; };
10BA0D471CE74E3D00887C2B /* RNSVGRect.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = RNSVGRect.m; path = Shapes/RNSVGRect.m; sourceTree = "<group>"; };
/* End PBXFileReference section */
/* Begin PBXFrameworksBuildPhase section */
@ -115,34 +136,17 @@
0CF68AB81AF0540F00FF9E5C = {
isa = PBXGroup;
children = (
1039D29A1CE7212C001E90A8 /* Utils */,
1039D2801CE71DCF001E90A8 /* Elements */,
1039D27F1CE71D9B001E90A8 /* Text */,
1039D27E1CE71C70001E90A8 /* Shapes */,
0CF68AEA1AF0549300FF9E5C /* Brushes */,
0CF68AF81AF0549300FF9E5C /* ViewManagers */,
0CF68ADB1AF0549300FF9E5C /* RNSVGCGFloatArray.h */,
10FEAC6A1CC7D05200F1C23C /* RNSVGCGFCRule.h */,
0CF68ADC1AF0549300FF9E5C /* RNSVGContainer.h */,
0CF68ADD1AF0549300FF9E5C /* RNSVGGroup.h */,
0CF68ADE1AF0549300FF9E5C /* RNSVGGroup.m */,
10C068641CCF0F87007C6982 /* RNSVGShape.h */,
10C068651CCF0F87007C6982 /* RNSVGShape.m */,
108FD88D1CDAF0A300A65FB3 /* RNSVGImage.h */,
108FD88E1CDAF0A300A65FB3 /* RNSVGImage.m */,
10A063001CC7320C0000CEEF /* RNSVGPath.h */,
10A063011CC7320C0000CEEF /* RNSVGPath.m */,
1039D2A11CE721A7001E90A8 /* RNSVGContainer.h */,
0CF68ADF1AF0549300FF9E5C /* RNSVGNode.h */,
0CF68AE01AF0549300FF9E5C /* RNSVGNode.m */,
10A063021CC7320C0000CEEF /* RNSVGSvgView.h */,
10A063031CC7320C0000CEEF /* RNSVGSvgView.m */,
0CF68AE11AF0549300FF9E5C /* RNSVGRenderable.h */,
0CF68AE21AF0549300FF9E5C /* RNSVGRenderable.m */,
0CF68AE71AF0549300FF9E5C /* RNSVGText.h */,
0CF68AE81AF0549300FF9E5C /* RNSVGText.m */,
0CF68AE91AF0549300FF9E5C /* RNSVGTextFrame.h */,
0CF68AF61AF0549300FF9E5C /* RCTConvert+RNSVG.h */,
0CF68AF71AF0549300FF9E5C /* RCTConvert+RNSVG.m */,
10B898DD1CE4591F003CD3D4 /* RNSVGGlyphCache.h */,
10B898DE1CE45973003CD3D4 /* RNSVGGlyphCache.m */,
10B898E21CE4910A003CD3D4 /* UIBezierPath-Points.h */,
10B898E01CE490FC003CD3D4 /* UIBezierPath-Points.m */,
0CF68AC21AF0540F00FF9E5C /* Products */,
);
sourceTree = "<group>";
@ -175,26 +179,89 @@
0CF68AF81AF0549300FF9E5C /* ViewManagers */ = {
isa = PBXGroup;
children = (
108FD88A1CDAF09B00A65FB3 /* RNSVGImageManager.h */,
108FD88B1CDAF09B00A65FB3 /* RNSVGImageManager.m */,
10C068681CCF1061007C6982 /* RNSVGShapeManager.h */,
10C068691CCF1061007C6982 /* RNSVGShapeManager.m */,
10A062FA1CC732020000CEEF /* RNSVGPathManager.h */,
10A062FB1CC732020000CEEF /* RNSVGPathManager.m */,
10A062FC1CC732020000CEEF /* RNSVGSvgViewManager.h */,
10A062FD1CC732020000CEEF /* RNSVGSvgViewManager.m */,
0CF68AF91AF0549300FF9E5C /* RNSVGGroupManager.h */,
0CF68AFA1AF0549300FF9E5C /* RNSVGGroupManager.m */,
0CF68AFB1AF0549300FF9E5C /* RNSVGNodeManager.h */,
0CF68AFC1AF0549300FF9E5C /* RNSVGNodeManager.m */,
0CF68AFD1AF0549300FF9E5C /* RNSVGRenderableManager.h */,
0CF68AFE1AF0549300FF9E5C /* RNSVGRenderableManager.m */,
0CF68B031AF0549300FF9E5C /* RNSVGTextManager.h */,
0CF68B041AF0549300FF9E5C /* RNSVGTextManager.m */,
10BA0D1C1CE74E3100887C2B /* RNSVGCircleManager.h */,
10BA0D1D1CE74E3100887C2B /* RNSVGCircleManager.m */,
10BA0D1E1CE74E3100887C2B /* RNSVGEllipseManager.h */,
10BA0D1F1CE74E3100887C2B /* RNSVGEllipseManager.m */,
10BA0D201CE74E3100887C2B /* RNSVGGroupManager.h */,
10BA0D211CE74E3100887C2B /* RNSVGGroupManager.m */,
10BA0D221CE74E3100887C2B /* RNSVGImageManager.h */,
10BA0D231CE74E3100887C2B /* RNSVGImageManager.m */,
10BA0D241CE74E3100887C2B /* RNSVGLineManager.h */,
10BA0D251CE74E3100887C2B /* RNSVGLineManager.m */,
10BA0D261CE74E3100887C2B /* RNSVGNodeManager.h */,
10BA0D271CE74E3100887C2B /* RNSVGNodeManager.m */,
10BA0D281CE74E3100887C2B /* RNSVGPathManager.h */,
10BA0D291CE74E3100887C2B /* RNSVGPathManager.m */,
10BA0D2A1CE74E3100887C2B /* RNSVGRectManager.h */,
10BA0D2B1CE74E3100887C2B /* RNSVGRectManager.m */,
10BA0D2C1CE74E3100887C2B /* RNSVGRenderableManager.h */,
10BA0D2D1CE74E3100887C2B /* RNSVGRenderableManager.m */,
10BA0D301CE74E3100887C2B /* RNSVGSvgViewManager.h */,
10BA0D311CE74E3100887C2B /* RNSVGSvgViewManager.m */,
10BA0D321CE74E3100887C2B /* RNSVGTextManager.h */,
10BA0D331CE74E3100887C2B /* RNSVGTextManager.m */,
);
path = ViewManagers;
sourceTree = "<group>";
};
1039D27E1CE71C70001E90A8 /* Shapes */ = {
isa = PBXGroup;
children = (
10BA0D401CE74E3D00887C2B /* RNSVGCircle.h */,
10BA0D411CE74E3D00887C2B /* RNSVGCircle.m */,
10BA0D421CE74E3D00887C2B /* RNSVGEllipse.h */,
10BA0D431CE74E3D00887C2B /* RNSVGEllipse.m */,
10BA0D441CE74E3D00887C2B /* RNSVGLine.h */,
10BA0D451CE74E3D00887C2B /* RNSVGLine.m */,
10BA0D461CE74E3D00887C2B /* RNSVGRect.h */,
10BA0D471CE74E3D00887C2B /* RNSVGRect.m */,
);
name = Shapes;
sourceTree = "<group>";
};
1039D27F1CE71D9B001E90A8 /* Text */ = {
isa = PBXGroup;
children = (
1039D28D1CE71EC2001E90A8 /* RNSVGGlyphCache.h */,
1039D28E1CE71EC2001E90A8 /* RnSVGGlyphCache.m */,
1039D28F1CE71EC2001E90A8 /* RNSVGText.h */,
1039D2901CE71EC2001E90A8 /* RNSVGText.m */,
1039D2911CE71EC2001E90A8 /* RNSVGTextFrame.h */,
1039D2921CE71EC2001E90A8 /* UIBezierPath-Points.h */,
1039D2931CE71EC2001E90A8 /* UIBezierPath-Points.m */,
);
name = Text;
sourceTree = "<group>";
};
1039D2801CE71DCF001E90A8 /* Elements */ = {
isa = PBXGroup;
children = (
1039D2811CE71EB7001E90A8 /* RNSVGGroup.h */,
1039D2821CE71EB7001E90A8 /* RNSVGGroup.m */,
1039D2831CE71EB7001E90A8 /* RNSVGImage.h */,
1039D2841CE71EB7001E90A8 /* RNSVGImage.m */,
1039D2851CE71EB7001E90A8 /* RNSVGPath.h */,
1039D2861CE71EB7001E90A8 /* RNSVGPath.m */,
1039D2871CE71EB7001E90A8 /* RNSVGSvgView.h */,
1039D2881CE71EB7001E90A8 /* RNSVGSvgView.m */,
);
name = Elements;
sourceTree = "<group>";
};
1039D29A1CE7212C001E90A8 /* Utils */ = {
isa = PBXGroup;
children = (
1039D2AE1CE72F27001E90A8 /* RNSVGPercentageConverter.h */,
1039D2AF1CE72F27001E90A8 /* RNSVGPercentageConverter.m */,
1039D29B1CE72177001E90A8 /* RCTConvert+RNSVG.h */,
1039D29C1CE72177001E90A8 /* RCTConvert+RNSVG.m */,
1039D29D1CE72177001E90A8 /* RNSVGCGFCRule.h */,
1039D29E1CE72177001E90A8 /* RNSVGCGFloatArray.h */,
);
name = Utils;
sourceTree = "<group>";
};
/* End PBXGroup section */
/* Begin PBXNativeTarget section */
@ -250,30 +317,37 @@
isa = PBXSourcesBuildPhase;
buildActionMask = 2147483647;
files = (
10C068671CCF0F87007C6982 /* RNSVGShape.m in Sources */,
0CF68B161AF0549300FF9E5C /* RNSVGTextManager.m in Sources */,
10A063041CC7320C0000CEEF /* RNSVGPath.m in Sources */,
0CF68B111AF0549300FF9E5C /* RNSVGGroupManager.m in Sources */,
10BA0D3F1CE74E3100887C2B /* RNSVGTextManager.m in Sources */,
1039D28A1CE71EB7001E90A8 /* RNSVGImage.m in Sources */,
10BA0D4B1CE74E3D00887C2B /* RNSVGRect.m in Sources */,
10BA0D341CE74E3100887C2B /* RNSVGCircleManager.m in Sources */,
1039D2941CE71EC2001E90A8 /* RnSVGGlyphCache.m in Sources */,
1039D2B01CE72F27001E90A8 /* RNSVGPercentageConverter.m in Sources */,
10BA0D491CE74E3D00887C2B /* RNSVGEllipse.m in Sources */,
1039D28B1CE71EB7001E90A8 /* RNSVGPath.m in Sources */,
0CF68B0D1AF0549300FF9E5C /* RNSVGPattern.m in Sources */,
0CF68B0A1AF0549300FF9E5C /* RNSVGText.m in Sources */,
0CF68B121AF0549300FF9E5C /* RNSVGNodeManager.m in Sources */,
0CF68B051AF0549300FF9E5C /* RNSVGGroup.m in Sources */,
10A062FF1CC732020000CEEF /* RNSVGSvgViewManager.m in Sources */,
0CF68B131AF0549300FF9E5C /* RNSVGRenderableManager.m in Sources */,
108FD88F1CDAF0A300A65FB3 /* RNSVGImage.m in Sources */,
0CF68B0E1AF0549300FF9E5C /* RNSVGRadialGradient.m in Sources */,
10A063051CC7320C0000CEEF /* RNSVGSvgView.m in Sources */,
1039D2951CE71EC2001E90A8 /* RNSVGText.m in Sources */,
10BA0D3B1CE74E3100887C2B /* RNSVGRectManager.m in Sources */,
0CF68B071AF0549300FF9E5C /* RNSVGRenderable.m in Sources */,
10B898E11CE490FC003CD3D4 /* UIBezierPath-Points.m in Sources */,
0CF68B101AF0549300FF9E5C /* RCTConvert+RNSVG.m in Sources */,
10C0686A1CCF1061007C6982 /* RNSVGShapeManager.m in Sources */,
108FD88C1CDAF09B00A65FB3 /* RNSVGImageManager.m in Sources */,
10A062FE1CC732020000CEEF /* RNSVGPathManager.m in Sources */,
1039D2891CE71EB7001E90A8 /* RNSVGGroup.m in Sources */,
0CF68B061AF0549300FF9E5C /* RNSVGNode.m in Sources */,
10BA0D3E1CE74E3100887C2B /* RNSVGSvgViewManager.m in Sources */,
0CF68B0F1AF0549300FF9E5C /* RNSVGSolidColor.m in Sources */,
10BA0D3A1CE74E3100887C2B /* RNSVGPathManager.m in Sources */,
1039D2961CE71EC2001E90A8 /* UIBezierPath-Points.m in Sources */,
10BA0D3C1CE74E3100887C2B /* RNSVGRenderableManager.m in Sources */,
0CF68B0C1AF0549300FF9E5C /* RNSVGLinearGradient.m in Sources */,
10B898DF1CE45973003CD3D4 /* RNSVGGlyphCache.m in Sources */,
10BA0D371CE74E3100887C2B /* RNSVGImageManager.m in Sources */,
10BA0D391CE74E3100887C2B /* RNSVGNodeManager.m in Sources */,
10BA0D381CE74E3100887C2B /* RNSVGLineManager.m in Sources */,
10BA0D481CE74E3D00887C2B /* RNSVGCircle.m in Sources */,
10BA0D351CE74E3100887C2B /* RNSVGEllipseManager.m in Sources */,
1039D2A01CE72177001E90A8 /* RCTConvert+RNSVG.m in Sources */,
0CF68B0B1AF0549300FF9E5C /* RNSVGBrush.m in Sources */,
10BA0D361CE74E3100887C2B /* RNSVGGroupManager.m in Sources */,
10BA0D4A1CE74E3D00887C2B /* RNSVGLine.m in Sources */,
1039D28C1CE71EB7001E90A8 /* RNSVGSvgView.m in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
};

Просмотреть файл

@ -50,7 +50,7 @@ static NSMutableDictionary *ClipPaths;
- (void)renderTo:(CGContextRef)context
{
float opacity = self.opacity;
if (opacity <= 0) {
// Nothing to paint
return;
@ -60,7 +60,7 @@ static NSMutableDictionary *ClipPaths;
if (!transparent) {
opacity = 1;
}
// This needs to be painted on a layer before being composited.
CGContextSaveGState(context);
CGContextConcatCTM(context, self.transform);
@ -101,20 +101,6 @@ static NSMutableDictionary *ClipPaths;
[ClipPaths setValue:[NSValue valueWithPointer:_clipPath] forKey:clipPathId];
}
- (void)dealloc
{
CGPathRelease(_clipPath);
if (definedClipPathId) {
[ClipPaths removeObjectForKey:definedClipPathId];
}
}
- (void)renderLayerTo:(CGContextRef)context
{
// abstract
}
- (CGPathRef)getPath: (CGContextRef) context
{
// abstract
@ -141,4 +127,22 @@ static NSMutableDictionary *ClipPaths;
}
}
- (void)reactSetInheritedBackgroundColor:(UIColor *)inheritedBackgroundColor
{
self.backgroundColor = inheritedBackgroundColor;
}
- (void)renderLayerTo:(CGContextRef)context
{
// abstract
}
- (void)dealloc
{
CGPathRelease(_clipPath);
if (definedClipPathId) {
[ClipPaths removeObjectForKey:definedClipPathId];
}
}
@end

Просмотреть файл

@ -23,6 +23,7 @@
@property (nonatomic, assign) CGLineJoin strokeLinejoin;
@property (nonatomic, assign) RNSVGCGFloatArray strokeDasharray;
@property (nonatomic, assign) CGFloat strokeDashoffset;
@property (nonatomic, assign) CGMutablePathRef nodeArea;
- (CGFloat)getActualProp:(NSDictionary *) prop relative:(float)relative;

Просмотреть файл

@ -10,6 +10,15 @@
@implementation RNSVGRenderable
- (id)init
{
self = [super init];
if (self) {
_nodeArea = CGPathCreateMutable();
}
return self;
}
- (void)setFill:(RNSVGBrush *)fill
{
[self invalidate];
@ -60,6 +69,7 @@
- (void)dealloc
{
CGPathRelease(_nodeArea);
if (_strokeDasharray.array) {
free(_strokeDasharray.array);
}
@ -91,6 +101,16 @@
}
}
// hitTest delagate
- (UIView *)hitTest:(CGPoint)point
withEvent:(UIEvent *)event
{
if (self.nodeArea != NULL && CGPathContainsPoint(self.nodeArea, nil, point, NO)) {
return self;
} else {
return nil;
}
}
- (void)renderLayerTo:(CGContextRef)context
{

Просмотреть файл

@ -102,7 +102,6 @@
}
default:
RCTLogError(@"Invalid Shape type %d at %@", type, self.shape);
//CGPathRelease(path);
}

21
ios/Shapes/RNSVGCircle.h Normal file
Просмотреть файл

@ -0,0 +1,21 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <Foundation/Foundation.h>
#import "RNSVGRenderable.h"
#import "RNSVGPath.h"
@interface RNSVGCircle : RNSVGPath
@property (nonatomic, strong) NSString* cx;
@property (nonatomic, strong) NSString* cy;
@property (nonatomic, strong) NSString* r;
@end

78
ios/Shapes/RNSVGCircle.m Normal file
Просмотреть файл

@ -0,0 +1,78 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGCircle.h"
#import "RCTLog.h"
@implementation RNSVGCircle
- (void)setCx:(NSString *)cx
{
if (cx == _cx) {
return;
}
[self invalidate];
_cx = cx;
}
- (void)setCy:(NSString *)cy
{
if (cy == _cy) {
return;
}
[self invalidate];
_cy = cy;
}
- (void)setR:(NSString *)r
{
if (r == _r) {
return;
}
[self invalidate];
_r = r;
}
- (void)renderLayerTo:(CGContextRef)context
{
self.d = [self getPath: context];
[super renderLayerTo:context];
}
- (CGPathRef)getPath:(CGContextRef)context
{
CGMutablePathRef path = CGPathCreateMutable();
CGRect box = CGContextGetClipBoundingBox(context);
float height = CGRectGetHeight(box);
float width = CGRectGetWidth(box);
RNSVGPercentageConverter* convert = [[RNSVGPercentageConverter alloc] init];
CGFloat cx = [convert stringToFloat:self.cx relative:width offset:0];
CGFloat cy = [convert stringToFloat:self.cy relative:height offset:0];
CGFloat r;
// radius in percentage calculate formula:
// radius = sqrt(pow((width*percent), 2) + pow((height*percent), 2)) / sqrt(2)
if ([convert isPercentage:self.r]) {
CGFloat radiusPercent = [convert percentageToFloat:self.r relative:1 offset:0];
r = sqrt(pow((width * radiusPercent), 2) + pow((height * radiusPercent), 2)) / sqrt(2);
} else {
r = [self.r floatValue];
}
CGPathAddArc(path, nil, cx, cy, r, 0, 2*M_PI, YES);
return path;
}
- (CGFloat)getActualProp:(NSString *)name relative:(float)relative
{
return 0;
}
@end

19
ios/Shapes/RNSVGEllipse.h Normal file
Просмотреть файл

@ -0,0 +1,19 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <Foundation/Foundation.h>
#import "RNSVGRenderable.h"
#import "RNSVGPath.h"
@interface RNSVGEllipse : RNSVGPath
@property (nonatomic, strong) NSString* cx;
@property (nonatomic, strong) NSString* cy;
@property (nonatomic, strong) NSString* rx;
@property (nonatomic, strong) NSString* ry;
@end

73
ios/Shapes/RNSVGEllipse.m Normal file
Просмотреть файл

@ -0,0 +1,73 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGEllipse.h"
#import "RCTLog.h"
@implementation RNSVGEllipse
- (void)setCx:(NSString *)cx
{
if (cx == _cx) {
return;
}
[self invalidate];
_cx = cx;
}
- (void)setCy:(NSString *)cy
{
if (cy == _cy) {
return;
}
[self invalidate];
_cy = cy;
}
- (void)setRx:(NSString *)rx
{
if (rx == _rx) {
return;
}
[self invalidate];
_rx = rx;
}
- (void)setRy:(NSString *)ry
{
if (ry == _ry) {
return;
}
[self invalidate];
_ry = ry;
}
- (void)renderLayerTo:(CGContextRef)context
{
self.d = [self getPath: context];
[super renderLayerTo:context];
}
- (CGPathRef)getPath:(CGContextRef)context
{
CGMutablePathRef path = CGPathCreateMutable();
CGRect box = CGContextGetClipBoundingBox(context);
float height = CGRectGetHeight(box);
float width = CGRectGetWidth(box);
RNSVGPercentageConverter* convert = [[RNSVGPercentageConverter alloc] init];
CGFloat cx = [convert stringToFloat:self.cx relative:width offset:0];
CGFloat cy = [convert stringToFloat:self.cy relative:height offset:0];
CGFloat rx = [convert stringToFloat:self.rx relative:width offset:0];
CGFloat ry = [convert stringToFloat:self.ry relative:height offset:0];
CGPathAddEllipseInRect(path, nil, CGRectMake(cx - rx, cy - ry, rx * 2, ry * 2));
return path;
}
@end

19
ios/Shapes/RNSVGLine.h Normal file
Просмотреть файл

@ -0,0 +1,19 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <Foundation/Foundation.h>
#import "RNSVGRenderable.h"
#import "RNSVGPath.h"
@interface RNSVGLine : RNSVGPath
@property (nonatomic, strong) NSString* x1;
@property (nonatomic, strong) NSString* y1;
@property (nonatomic, strong) NSString* x2;
@property (nonatomic, strong) NSString* y2;
@end

75
ios/Shapes/RNSVGLine.m Normal file
Просмотреть файл

@ -0,0 +1,75 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGLine.h"
#import "RCTLog.h"
@implementation RNSVGLine
- (void)setX1:(NSString *)x1
{
if (x1 == _x1) {
return;
}
[self invalidate];
_x1 = x1;
}
- (void)setY1:(NSString *)y1
{
if (y1 == _y1) {
return;
}
[self invalidate];
_y1 = y1;
}
- (void)setX2:(NSString *)x2
{
if (x2 == _x2) {
return;
}
[self invalidate];
_x2 = x2;
}
- (void)setY2:(NSString *)y2
{
if (y2 == _y2) {
return;
}
[self invalidate];
_y2 = y2;
}
- (void)renderLayerTo:(CGContextRef)context
{
self.d = [self getPath: context];
[super renderLayerTo:context];
}
- (CGPathRef)getPath:(CGContextRef)context
{
CGMutablePathRef path = CGPathCreateMutable();
CGRect box = CGContextGetClipBoundingBox(context);
float height = CGRectGetHeight(box);
float width = CGRectGetWidth(box);
RNSVGPercentageConverter* convert = [[RNSVGPercentageConverter alloc] init];
CGFloat x1 = [convert stringToFloat:self.x1 relative:width offset:0];
CGFloat y1 = [convert stringToFloat:self.y1 relative:height offset:0];
CGFloat x2 = [convert stringToFloat:self.x2 relative:width offset:0];
CGFloat y2 = [convert stringToFloat:self.y2 relative:height offset:0];
CGPathMoveToPoint(path, nil, x1, y1);
CGPathAddLineToPoint(path, nil, x2, y2);
return path;
}
@end

23
ios/Shapes/RNSVGRect.h Normal file
Просмотреть файл

@ -0,0 +1,23 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <Foundation/Foundation.h>
#import "RNSVGRenderable.h"
#import "RNSVGPath.h"
@interface RNSVGRect : RNSVGPath
@property (nonatomic, strong) NSString* x;
@property (nonatomic, strong) NSString* y;
@property (nonatomic, strong) NSString* width;
@property (nonatomic, strong) NSString* height;
@property (nonatomic, strong) NSString* rx;
@property (nonatomic, strong) NSString* ry;
@end

115
ios/Shapes/RNSVGRect.m Normal file
Просмотреть файл

@ -0,0 +1,115 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGRect.h"
#import "RCTLog.h"
@implementation RNSVGRect
- (void)setX:(NSString *)x
{
if (x == _x) {
return;
}
[self invalidate];
_x = x;
}
- (void)setY:(NSString *)y
{
if (y == _y) {
return;
}
[self invalidate];
_y = y;
}
- (void)setWidth:(NSString *)width
{
if (width == _width) {
return;
}
[self invalidate];
_width = width;
}
- (void)setHeight:(NSString *)height
{
if (height == _height) {
return;
}
[self invalidate];
_height = height;
}
- (void)setRx:(NSString *)rx
{
if (rx == _rx) {
return;
}
[self invalidate];
_rx = rx;
}
- (void)setRy:(NSString *)ry
{
if (ry == _ry) {
return;
}
[self invalidate];
_ry = ry;
}
- (void)renderLayerTo:(CGContextRef)context
{
self.d = [self getPath: context];
[super renderLayerTo:context];
}
- (CGPathRef)getPath:(CGContextRef)context
{
CGMutablePathRef path = CGPathCreateMutable();
CGRect box = CGContextGetClipBoundingBox(context);
float height = CGRectGetHeight(box);
float width = CGRectGetWidth(box);
RNSVGPercentageConverter* convert = [[RNSVGPercentageConverter alloc] init];
CGFloat x = [convert stringToFloat:self.x relative:width offset:0];
CGFloat y = [convert stringToFloat:self.y relative:height offset:0];
CGFloat w = [convert stringToFloat:self.width relative:width offset:0];
CGFloat h = [convert stringToFloat:self.height relative:height offset:0];
CGFloat rx = [convert stringToFloat:self.rx relative:width offset:0];
CGFloat ry = [convert stringToFloat:self.ry relative:height offset:0];
if (rx != 0 || ry != 0) {
if (rx == 0) {
rx = ry;
} else if (ry == 0) {
ry = rx;
}
if (rx > w / 2) {
rx = w / 2;
}
if (ry > h / 2) {
ry = h / 2;
}
CGPathAddRoundedRect(path, nil, CGRectMake(x, y, w, h), rx, ry);
} else {
CGPathAddRect(path, nil, CGRectMake(x, y, w, h));
}
return path;
}
@end

Просмотреть файл

@ -0,0 +1,27 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
// This implements a very simple glyph cache.
// It maps from CTFontRef to CGGlyph to CGPathRef in order to reuse glyphs.
// It does NOT try to retain the keys that are used (CTFontRef or CGGlyph)
// but that is not an issue with respect to how it is used by this sample.
#import <Foundation/Foundation.h>
#import <CoreText/CoreText.h>
#import "RNSVGRenderable.h"
@interface RNSVGGlyphCache : NSObject
{
CFMutableDictionaryRef cache;
}
- (id)init;
- (CGPathRef)pathForGlyph:(CGGlyph)glyph fromFont:(CTFontRef)font;
@end

21
ios/Text/RNSVGText.h Normal file
Просмотреть файл

@ -0,0 +1,21 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <Foundation/Foundation.h>
#import "UIBezierPath-Points.h"
#import "RNSVGPath.h"
#import "RNSVGTextFrame.h"
#import "RNSVGGlyphCache.h"
@interface RNSVGText : RNSVGPath
@property (nonatomic, assign) CTTextAlignment alignment;
@property (nonatomic, assign) RNSVGTextFrame textFrame;
@property (nonatomic, assign) CGPathRef path;
@end

148
ios/Text/RNSVGText.m Normal file
Просмотреть файл

@ -0,0 +1,148 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGText.h"
#import <CoreText/CoreText.h>
@implementation RNSVGText
static void RNSVGFreeTextFrame(RNSVGTextFrame frame)
{
if (frame.count) {
// We must release each line before freeing up this struct
for (int i = 0; i < frame.count; i++) {
CFRelease(frame.lines[i]);
}
free(frame.lines);
free(frame.widths);
}
}
- (void)setAlignment:(CTTextAlignment)alignment
{
[self invalidate];
_alignment = alignment;
}
- (void)setTextFrame:(RNSVGTextFrame)frame
{
if (frame.lines != _textFrame.lines) {
RNSVGFreeTextFrame(_textFrame);
}
[self invalidate];
_textFrame = frame;
}
- (void)setPath:(CGPathRef)path
{
if (path == _path) {
return;
}
[self invalidate];
CGPathRelease(_path);
_path = CGPathRetain(path);
}
- (void)dealloc
{
CGPathRelease(_path);
RNSVGFreeTextFrame(_textFrame);
}
- (void)renderLayerTo:(CGContextRef)context
{
self.d = [self getPath: context];
[super renderLayerTo:context];
}
- (CGPathRef)getPath:(CGContextRef)context
{
CGMutablePathRef path = CGPathCreateMutable();
RNSVGTextFrame frame = self.textFrame;
for (int i = 0; i < frame.count; i++) {
CGFloat shift;
CGFloat width = frame.widths[i];
switch (self.alignment) {
case kCTTextAlignmentRight:
shift = width;
break;
case kCTTextAlignmentCenter:
shift = width / 2;
break;
default:
shift = 0;
break;
}
// We should consider snapping this shift to device pixels to improve rendering quality
// when a line has subpixel width.
CGAffineTransform offset = CGAffineTransformMakeTranslation(-shift, frame.baseLine + frame.lineHeight * i + (self.path == NULL ? 0 : -frame.lineHeight));
CGPathAddPath(path, &offset, [self setLinePath:frame.lines[i]]);
}
return path;
}
- (CGPathRef)setLinePath:(CTLineRef)line
{
CGAffineTransform upsideDown = CGAffineTransformMakeScale(1.0, -1.0);
CGMutablePathRef path = CGPathCreateMutable();
RNSVGGlyphCache *cache = [[RNSVGGlyphCache alloc] init];
CTLineGetGlyphRuns(line);
CFArrayRef glyphRuns = CTLineGetGlyphRuns(line);
CFIndex runCount = CFArrayGetCount(glyphRuns);
CFIndex glyphIndex = 0;
for(CFIndex i = 0; i < runCount; ++i)
{
// For each run, we need to get the glyphs, their font (to get the path) and their locations.
CTRunRef run = CFArrayGetValueAtIndex(glyphRuns, i);
CFIndex runGlyphCount = CTRunGetGlyphCount(run);
CGPoint positions[runGlyphCount];
CGGlyph glyphs[runGlyphCount];
// Grab the glyphs, positions, and font
CTRunGetPositions(run, CFRangeMake(0, 0), positions);
CTRunGetGlyphs(run, CFRangeMake(0, 0), glyphs);
CFDictionaryRef attributes = CTRunGetAttributes(run);
CTFontRef runFont = CFDictionaryGetValue(attributes, kCTFontAttributeName);
for(CFIndex j = 0; j < runGlyphCount; ++j, ++glyphIndex) {
CGPathRef letter = [cache pathForGlyph:glyphs[j] fromFont:runFont];
CGPoint point = positions[j];
if (letter != NULL) {
CGAffineTransform transform;
// draw glyphs along path
if (self.path != NULL) {
CGPoint slope;
CGRect bounding = CGPathGetBoundingBox(letter);
UIBezierPath* path = [UIBezierPath bezierPathWithCGPath:self.path];
CGFloat percentConsumed = (point.x + bounding.size.width) / path.length;
if (percentConsumed >= 1.0f) {
continue;
}
CGPoint targetPoint = [path pointAtPercent:percentConsumed withSlope: &slope];
float angle = atan(slope.y / slope.x); // + M_PI;
if (slope.x < 0) angle += M_PI; // going left, update the angle
transform = CGAffineTransformMakeTranslation(targetPoint.x - bounding.size.width, targetPoint.y);
transform = CGAffineTransformRotate(transform, angle);
transform = CGAffineTransformScale(transform, 1.0, -1.0);
} else {
transform = CGAffineTransformTranslate(upsideDown, point.x, point.y);
}
CGPathAddPath(path, &transform, letter);
}
}
}
return path;
}
@end

24
ios/Text/RNSVGTextFrame.h Normal file
Просмотреть файл

@ -0,0 +1,24 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <CoreText/CoreText.h>
// A little helper to make sure we have a set of lines including width ready for use.
// We assume that we will only this in one place so no reference counting is necessary.
// Needs to be freed when dealloced.
// This is fragile since this relies on these values not getting reused. Consider
// wrapping these in an Obj-C class or some ARC hackery to get refcounting.
typedef struct {
size_t count;
CGFloat baseLine; // Distance from the origin to the base line of the first line
CGFloat lineHeight; // Distance between lines
CTLineRef *lines;
CGFloat *widths; // Width of each line
} RNSVGTextFrame;

Просмотреть файл

@ -0,0 +1,63 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGGlyphCache.h"
@implementation RNSVGGlyphCache
-(id)init
{
self = [super init];
if(self != nil)
{
cache = CFDictionaryCreateMutable(kCFAllocatorDefault, 0, NULL, &kCFTypeDictionaryValueCallBacks);
}
return self;
}
-(void)dealloc
{
CFRelease(cache);
}
-(CGPathRef)pathForGlyph:(CGGlyph)glyph fromFont:(CTFontRef)font
{
// First we lookup the font to get to its glyph dictionary
CFMutableDictionaryRef glyphDict = (CFMutableDictionaryRef)CFDictionaryGetValue(cache, font);
if(glyphDict == NULL)
{
// And if this font hasn't been seen before, we'll create and set the dictionary for it
glyphDict = CFDictionaryCreateMutable(kCFAllocatorDefault, 0, NULL, &kCFTypeDictionaryValueCallBacks);
CFDictionarySetValue(cache, font, glyphDict);
CFRelease(glyphDict);
}
// Next we try to get a path for the given glyph from the glyph dictionary
CGPathRef path = (CGPathRef)CFDictionaryGetValue(glyphDict, (const void *)(uintptr_t)glyph);
if(path == NULL)
{
// If the path hasn't been seen before, then we'll create the path from the font & glyph and cache it.
path = CTFontCreatePathForGlyph(font, glyph, NULL);
if(path == NULL)
{
// If a glyph does not have a path, then we need a placeholder to set in the dictionary
path = (CGPathRef)kCFNull;
}
CFDictionarySetValue(glyphDict, (const void *)(uintptr_t)glyph, path);
CFRelease(path);
}
if(path == (CGPathRef)kCFNull)
{
// If we got the placeholder, then set the path to NULL
// (this will happen either after discovering the glyph path is NULL,
// or after looking that up in the dictionary).
path = NULL;
}
return path;
}
@end

Просмотреть файл

@ -0,0 +1,27 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
/*
Erica Sadun, http://ericasadun.com
iPhone Developer's Cookbook, 6.x Edition
BSD License, Use at your own risk
*/
#import <Foundation/Foundation.h>
#import <UIKit/UIKit.h>
@interface UIBezierPath (Points)
@property (nonatomic, readonly) NSArray *points;
@property (nonatomic, readonly) NSArray *bezierElements;
@property (nonatomic, readonly) CGFloat length;
- (NSArray *) pointPercentArray;
- (CGPoint) pointAtPercent: (CGFloat) percent withSlope: (CGPoint *) slope;
+ (UIBezierPath *) pathWithPoints: (NSArray *) points;
+ (UIBezierPath *) pathWithElements: (NSArray *) elements;
@end

Просмотреть файл

@ -0,0 +1,219 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
/*
Erica Sadun, http://ericasadun.com
iPhone Developer's Cookbook, 6.x Edition
BSD License, Use at your own risk
*/
#import "UIBezierPath-Points.h"
#define POINTSTRING(_CGPOINT_) (NSStringFromCGPoint(_CGPOINT_))
#define VALUE(_INDEX_) [NSValue valueWithCGPoint:points[_INDEX_]]
#define POINT(_INDEX_) [(NSValue *)[points objectAtIndex:_INDEX_] CGPointValue]
// Return distance between two points
static float distance (CGPoint p1, CGPoint p2)
{
float dx = p2.x - p1.x;
float dy = p2.y - p1.y;
return sqrt(dx*dx + dy*dy);
}
@implementation UIBezierPath (Points)
void getPointsFromBezier(void *info, const CGPathElement *element)
{
NSMutableArray *bezierPoints = (__bridge NSMutableArray *)info;
CGPathElementType type = element->type;
CGPoint *points = element->points;
if (type != kCGPathElementCloseSubpath)
{
if ((type == kCGPathElementAddLineToPoint) ||
(type == kCGPathElementMoveToPoint))
[bezierPoints addObject:VALUE(0)];
else if (type == kCGPathElementAddQuadCurveToPoint)
[bezierPoints addObject:VALUE(1)];
else if (type == kCGPathElementAddCurveToPoint)
[bezierPoints addObject:VALUE(2)];
}
}
- (NSArray *)points
{
NSMutableArray *points = [NSMutableArray array];
CGPathApply(self.CGPath, (__bridge void *)points, getPointsFromBezier);
return points;
}
// Return a Bezier path buit with the supplied points
+ (UIBezierPath *) pathWithPoints: (NSArray *) points
{
UIBezierPath *path = [UIBezierPath bezierPath];
if (points.count == 0) return path;
[path moveToPoint:POINT(0)];
for (int i = 1; i < points.count; i++)
[path addLineToPoint:POINT(i)];
return path;
}
- (CGFloat) length
{
NSArray *points = self.points;
float totalPointLength = 0.0f;
for (int i = 1; i < points.count; i++)
totalPointLength += distance(POINT(i), POINT(i-1));
return totalPointLength;
}
- (NSArray *) pointPercentArray
{
// Use total length to calculate the percent of path consumed at each control point
NSArray *points = self.points;
int pointCount = points.count;
float totalPointLength = self.length;
float distanceTravelled = 0.0f;
NSMutableArray *pointPercentArray = [NSMutableArray array];
[pointPercentArray addObject:@(0.0)];
for (int i = 1; i < pointCount; i++)
{
distanceTravelled += distance(POINT(i), POINT(i-1));
[pointPercentArray addObject:@(distanceTravelled / totalPointLength)];
}
// Add a final item just to stop with. Probably not needed.
[pointPercentArray addObject:[NSNumber numberWithFloat:1.1f]]; // 110%
return pointPercentArray;
}
- (CGPoint) pointAtPercent: (CGFloat) percent withSlope: (CGPoint *) slope
{
NSArray *points = self.points;
NSArray *percentArray = self.pointPercentArray;
CFIndex lastPointIndex = points.count - 1;
if (!points.count) {
return CGPointZero;
}
// Check for 0% and 100%
if (percent <= 0.0f) {
return POINT(0);
}
if (percent >= 1.0f) {
return POINT(lastPointIndex);
}
// Find a corresponding pair of points in the path
CFIndex index = 1;
while ((index < percentArray.count) &&
(percent > ((NSNumber *)percentArray[index]).floatValue)) {
index++;
}
// This should not happen.
if (index > lastPointIndex) {
return POINT(lastPointIndex);
}
// Calculate the intermediate distance between the two points
CGPoint point1 = POINT(index -1);
CGPoint point2 = POINT(index);
float percent1 = [[percentArray objectAtIndex:index - 1] floatValue];
float percent2 = [[percentArray objectAtIndex:index] floatValue];
float percentOffset = (percent - percent1) / (percent2 - percent1);
float dx = point2.x - point1.x;
float dy = point2.y - point1.y;
// Store dy, dx for retrieving arctan
if (slope) {
*slope = CGPointMake(dx, dy);
}
// Calculate new point
CGFloat newX = point1.x + (percentOffset * dx);
CGFloat newY = point1.y + (percentOffset * dy);
CGPoint targetPoint = CGPointMake(newX, newY);
return targetPoint;
}
void getBezierElements(void *info, const CGPathElement *element)
{
NSMutableArray *bezierElements = (__bridge NSMutableArray *)info;
CGPathElementType type = element->type;
CGPoint *points = element->points;
switch (type)
{
case kCGPathElementCloseSubpath:
[bezierElements addObject:@[@(type)]];
break;
case kCGPathElementMoveToPoint:
case kCGPathElementAddLineToPoint:
[bezierElements addObject:@[@(type), VALUE(0)]];
break;
case kCGPathElementAddQuadCurveToPoint:
[bezierElements addObject:@[@(type), VALUE(0), VALUE(1)]];
break;
case kCGPathElementAddCurveToPoint:
[bezierElements addObject:@[@(type), VALUE(0), VALUE(1), VALUE(2)]];
break;
}
}
- (NSArray *) bezierElements
{
NSMutableArray *elements = [NSMutableArray array];
CGPathApply(self.CGPath, (__bridge void *)elements, getBezierElements);
return elements;
}
+ (UIBezierPath *) pathWithElements: (NSArray *) elements
{
UIBezierPath *path = [UIBezierPath bezierPath];
if (elements.count == 0) return path;
for (NSArray *points in elements)
{
if (!points.count) continue;
CGPathElementType elementType = [points[0] integerValue];
switch (elementType)
{
case kCGPathElementCloseSubpath:
[path closePath];
break;
case kCGPathElementMoveToPoint:
if (points.count == 2)
[path moveToPoint:POINT(1)];
break;
case kCGPathElementAddLineToPoint:
if (points.count == 2)
[path addLineToPoint:POINT(1)];
break;
case kCGPathElementAddQuadCurveToPoint:
if (points.count == 3)
[path addQuadCurveToPoint:POINT(2) controlPoint:POINT(1)];
break;
case kCGPathElementAddCurveToPoint:
if (points.count == 4)
[path addCurveToPoint:POINT(3) controlPoint1:POINT(1) controlPoint2:POINT(2)];
break;
}
}
return path;
}
@end

Просмотреть файл

@ -0,0 +1,31 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <QuartzCore/QuartzCore.h>
#import "RNSVGBrush.h"
#import "RNSVGCGFloatArray.h"
#import "RNSVGTextFrame.h"
#import "RCTConvert.h"
#import "RNSVGCGFCRule.h"
@interface RCTConvert (RNSVG)
+ (CGPathRef)CGPath:(id)json;
+ (CTTextAlignment)CTTextAlignment:(id)json;
+ (RNSVGCGFCRule)RNSVGCGFCRule:(id)json;
+ (RNSVGTextFrame)RNSVGTextFrame:(id)json;
+ (RNSVGCGFloatArray)RNSVGCGFloatArray:(id)json;
+ (RNSVGBrush *)RNSVGBrush:(id)json;
+ (CGPoint)CGPoint:(id)json offset:(NSUInteger)offset;
+ (CGRect)CGRect:(id)json offset:(NSUInteger)offset;
+ (CGColorRef)CGColor:(id)json offset:(NSUInteger)offset;
+ (CGGradientRef)CGGradient:(id)json offset:(NSUInteger)offset;
@end

Просмотреть файл

@ -0,0 +1,231 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RCTConvert+RNSVG.h"
#import "RNSVGLinearGradient.h"
#import "RNSVGPattern.h"
#import "RNSVGRadialGradient.h"
#import "RNSVGSolidColor.h"
#import "RCTLog.h"
#import "RNSVGCGFCRule.h"
@implementation RCTConvert (RNSVG)
+ (CGPathRef)CGPath:(id)json
{
NSArray *arr = [self NSNumberArray:json];
NSUInteger count = [arr count];
#define NEXT_VALUE [self double:arr[i++]]
CGMutablePathRef path = CGPathCreateMutable();
CGPathMoveToPoint(path, NULL, 0, 0);
@try {
NSUInteger i = 0;
while (i < count) {
NSUInteger type = [arr[i++] unsignedIntegerValue];
switch (type) {
case 0:
CGPathMoveToPoint(path, NULL, NEXT_VALUE, NEXT_VALUE);
break;
case 1:
CGPathCloseSubpath(path);
break;
case 2:
CGPathAddLineToPoint(path, NULL, NEXT_VALUE, NEXT_VALUE);
break;
case 3:
CGPathAddCurveToPoint(path, NULL, NEXT_VALUE, NEXT_VALUE, NEXT_VALUE, NEXT_VALUE, NEXT_VALUE, NEXT_VALUE);
break;
case 4:
CGPathAddArc(path, NULL, NEXT_VALUE, NEXT_VALUE, NEXT_VALUE, NEXT_VALUE, NEXT_VALUE, NEXT_VALUE == 0);
break;
default:
RCTLogError(@"Invalid CGPath type %zd at element %zd of %@", type, i, arr);
CGPathRelease(path);
return NULL;
}
}
}
@catch (NSException *exception) {
RCTLogError(@"Invalid CGPath format: %@", arr);
CGPathRelease(path);
return NULL;
}
return (CGPathRef)CFAutorelease(path);
}
RCT_ENUM_CONVERTER(CTTextAlignment, (@{
@"auto": @(kCTTextAlignmentNatural),
@"left": @(kCTTextAlignmentLeft),
@"center": @(kCTTextAlignmentCenter),
@"right": @(kCTTextAlignmentRight),
@"justify": @(kCTTextAlignmentJustified),
}), kCTTextAlignmentNatural, integerValue)
RCT_ENUM_CONVERTER(RNSVGCGFCRule, (@{
@"evenodd": @(kRNSVGCGFCRuleEvenodd),
@"nonzero": @(kRNSVGCGFCRuleNonzero),
}), kRNSVGCGFCRuleNonzero, intValue)
// This takes a tuple of text lines and a font to generate a CTLine for each text line.
// This prepares everything for rendering a frame of text in RNSVGText.
+ (RNSVGTextFrame)RNSVGTextFrame:(id)json
{
NSDictionary *dict = [self NSDictionary:json];
RNSVGTextFrame frame;
frame.count = 0;
NSArray *lines = [self NSArray:dict[@"lines"]];
NSUInteger lineCount = [lines count];
if (lineCount == 0) {
return frame;
}
NSDictionary *fontDict = dict[@"font"];
CTFontRef font = (__bridge CTFontRef)[self UIFont:nil withFamily:fontDict[@"fontFamily"] size:fontDict[@"fontSize"] weight:fontDict[@"fontWeight"] style:fontDict[@"fontStyle"] scaleMultiplier:1.0];
if (!font) {
return frame;
}
// Create a dictionary for this font
CFDictionaryRef attributes = (__bridge CFDictionaryRef)@{
(NSString *)kCTFontAttributeName: (__bridge id)font,
(NSString *)kCTForegroundColorFromContextAttributeName: @YES
};
// Set up text frame with font metrics
CGFloat size = CTFontGetSize(font);
frame.count = lineCount;
frame.baseLine = size; // estimate base line
frame.lineHeight = size * 1.1; // Base on RNSVG canvas line height estimate
frame.lines = malloc(sizeof(CTLineRef) * lineCount);
frame.widths = malloc(sizeof(CGFloat) * lineCount);
[lines enumerateObjectsUsingBlock:^(NSString *text, NSUInteger i, BOOL *stop) {
CFStringRef string = (__bridge CFStringRef)text;
CFAttributedStringRef attrString = CFAttributedStringCreate(kCFAllocatorDefault, string, attributes);
CTLineRef line = CTLineCreateWithAttributedString(attrString);
CFRelease(attrString);
frame.lines[i] = line;
frame.widths[i] = CTLineGetTypographicBounds(line, NULL, NULL, NULL);
}];
return frame;
}
+ (RNSVGCGFloatArray)RNSVGCGFloatArray:(id)json
{
NSArray *arr = [self NSNumberArray:json];
NSUInteger count = arr.count;
RNSVGCGFloatArray array;
array.count = count;
array.array = NULL;
if (count) {
// Ideally, these arrays should already use the same memory layout.
// In that case we shouldn't need this new malloc.
array.array = malloc(sizeof(CGFloat) * count);
for (NSUInteger i = 0; i < count; i++) {
array.array[i] = [arr[i] doubleValue];
}
}
return array;
}
+ (RNSVGBrush *)RNSVGBrush:(id)json
{
NSArray *arr = [self NSArray:json];
NSUInteger type = [self NSUInteger:arr.firstObject];
switch (type) {
case 0: // solid color
// These are probably expensive allocations since it's often the same value.
// We should memoize colors but look ups may be just as expensive.
return [[RNSVGSolidColor alloc] initWithArray:arr];
case 1: // linear gradient
return [[RNSVGLinearGradient alloc] initWithArray:arr];
case 2: // radial gradient
return [[RNSVGRadialGradient alloc] initWithArray:arr];
case 3: // pattern
// TODO:
return nil;
return [[RNSVGPattern alloc] initWithArray:arr];
default:
RCTLogError(@"Unknown brush type: %zd", type);
return nil;
}
}
+ (CGPoint)CGPoint:(id)json offset:(NSUInteger)offset
{
NSArray *arr = [self NSArray:json];
if (arr.count < offset + 2) {
RCTLogError(@"Too few elements in array (expected at least %zd): %@", 2 + offset, arr);
return CGPointZero;
}
return (CGPoint){
[self CGFloat:arr[offset]],
[self CGFloat:arr[offset + 1]],
};
}
+ (CGRect)CGRect:(id)json offset:(NSUInteger)offset
{
NSArray *arr = [self NSArray:json];
if (arr.count < offset + 4) {
RCTLogError(@"Too few elements in array (expected at least %zd): %@", 4 + offset, arr);
return CGRectZero;
}
return (CGRect){
{[self CGFloat:arr[offset]], [self CGFloat:arr[offset + 1]]},
{[self CGFloat:arr[offset + 2]], [self CGFloat:arr[offset + 3]]},
};
}
+ (CGColorRef)CGColor:(id)json offset:(NSUInteger)offset
{
NSArray *arr = [self NSArray:json];
if (arr.count < offset + 4) {
RCTLogError(@"Too few elements in array (expected at least %zd): %@", 4 + offset, arr);
return NULL;
}
return [self CGColor:[arr subarrayWithRange:(NSRange){offset, 4}]];
}
+ (CGGradientRef)CGGradient:(id)json offset:(NSUInteger)offset
{
NSArray *arr = [self NSArray:json];
if (arr.count < offset) {
RCTLogError(@"Too few elements in array (expected at least %zd): %@", offset, arr);
return NULL;
}
arr = [arr subarrayWithRange:(NSRange){offset, arr.count - offset}];
RNSVGCGFloatArray colorsAndOffsets = [self RNSVGCGFloatArray:arr];
size_t stops = colorsAndOffsets.count / 5;
CGColorSpaceRef rgb = CGColorSpaceCreateDeviceRGB();
CGGradientRef gradient = CGGradientCreateWithColorComponents(
rgb,
colorsAndOffsets.array,
colorsAndOffsets.array + stops * 4,
stops
);
CGColorSpaceRelease(rgb);
free(colorsAndOffsets.array);
return (CGGradientRef)CFAutorelease(gradient);
}
@end

12
ios/Utils/RNSVGCGFCRule.h Normal file
Просмотреть файл

@ -0,0 +1,12 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
typedef CF_ENUM(int32_t, RNSVGCGFCRule) {
kRNSVGCGFCRuleEvenodd,
kRNSVGCGFCRuleNonzero
};

Просмотреть файл

@ -0,0 +1,19 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
// A little helper to make sure we have the right memory allocation ready for use.
// We assume that we will only this in one place so no reference counting is necessary.
// Needs to be freed when dealloced.
// This is fragile since this relies on these values not getting reused. Consider
// wrapping these in an Obj-C class or some ARC hackery to get refcounting.
typedef struct {
size_t count;
CGFloat *array;
} RNSVGCGFloatArray;

Просмотреть файл

@ -0,0 +1,21 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <Foundation/Foundation.h>
@interface RNSVGPercentageConverter : NSObject
- (NSRegularExpression *) getPercentageRegularExpression;
- (float) percentageToFloat:(NSString *)percentage relative:(float)relative offset:(float)offset;
- (float) stringToFloat:(NSString *)string relative:(float)relative offset:(float)offset;
- (BOOL) isPercentage:(NSString *) string;
@end

Просмотреть файл

@ -0,0 +1,62 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGPercentageConverter.h"
@implementation RNSVGPercentageConverter
{
NSRegularExpression *percentageRegularExpression;
}
- (id)init
{
self = [super init];
if (self) {
percentageRegularExpression = [[NSRegularExpression alloc] initWithPattern:@"^(\\-?\\d+(?:\\.\\d+)?)%$" options:0 error:nil];
}
return self;
}
- (NSRegularExpression *) getPercentageRegularExpression
{
return percentageRegularExpression;
}
- (float) stringToFloat:(NSString *)percentage relative:(float)relative offset:(float)offset
{
if ([self isPercentage:percentage] == NO) {
return [percentage floatValue];
} else {
return [self percentageToFloat:percentage relative:relative offset:offset];
}
}
- (float) percentageToFloat:(NSString *)percentage relative:(float)relative offset:(float)offset
{
__block float matched;
[percentageRegularExpression enumerateMatchesInString:percentage
options:0
range:NSMakeRange(0, percentage.length)
usingBlock:^(NSTextCheckingResult *result, NSMatchingFlags flags, BOOL *stop)
{
matched = [[percentage substringWithRange:NSMakeRange(result.range.location, result.range.length)] floatValue];
matched = matched / 100 * relative + offset;
}];
return matched;
}
- (BOOL) isPercentage:(NSString *) string
{
return [percentageRegularExpression firstMatchInString:string options:0 range:NSMakeRange(0, [string length])] != NULL;
}
@end

Просмотреть файл

@ -0,0 +1,13 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGRenderableManager.h"
@interface RNSVGCircleManager : RNSVGRenderableManager
@end

Просмотреть файл

@ -0,0 +1,39 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGCircleManager.h"
#import "RNSVGCircle.h"
#import "RCTConvert+RNSVG.h"
@implementation RNSVGCircleManager
RCT_EXPORT_MODULE()
- (RNSVGRenderable *)node
{
return [RNSVGCircle new];
}
RCT_EXPORT_VIEW_PROPERTY(cx, NSString)
RCT_EXPORT_VIEW_PROPERTY(cy, NSString)
RCT_EXPORT_VIEW_PROPERTY(r, NSString)
// fix me: these should inherited from renderable
RCT_EXPORT_VIEW_PROPERTY(fill, RNSVGBrush)
RCT_EXPORT_VIEW_PROPERTY(fillRule, RNSVGCGFCRule)
RCT_EXPORT_VIEW_PROPERTY(stroke, RNSVGBrush)
RCT_EXPORT_VIEW_PROPERTY(strokeWidth, CGFloat)
RCT_EXPORT_VIEW_PROPERTY(strokeLinecap, CGLineCap)
RCT_EXPORT_VIEW_PROPERTY(strokeLinejoin, CGLineJoin)
RCT_EXPORT_VIEW_PROPERTY(clipPath, CGPath)
RCT_EXPORT_VIEW_PROPERTY(clipRule, RNSVGCGFCRule)
RCT_EXPORT_VIEW_PROPERTY(strokeDasharray, RNSVGCGFloatArray)
RCT_EXPORT_VIEW_PROPERTY(strokeDashoffset, CGFloat)
@end

Просмотреть файл

@ -0,0 +1,13 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGRenderableManager.h"
@interface RNSVGEllipseManager : RNSVGRenderableManager
@end

Просмотреть файл

@ -0,0 +1,40 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGEllipseManager.h"
#import "RNSVGEllipse.h"
#import "RCTConvert+RNSVG.h"
@implementation RNSVGEllipseManager
RCT_EXPORT_MODULE()
- (RNSVGRenderable *)node
{
return [RNSVGEllipse new];
}
RCT_EXPORT_VIEW_PROPERTY(cx, NSString)
RCT_EXPORT_VIEW_PROPERTY(cy, NSString)
RCT_EXPORT_VIEW_PROPERTY(rx, NSString)
RCT_EXPORT_VIEW_PROPERTY(ry, NSString)
// fix me: these should inherited from renderable
RCT_EXPORT_VIEW_PROPERTY(fill, RNSVGBrush)
RCT_EXPORT_VIEW_PROPERTY(fillRule, RNSVGCGFCRule)
RCT_EXPORT_VIEW_PROPERTY(stroke, RNSVGBrush)
RCT_EXPORT_VIEW_PROPERTY(strokeWidth, CGFloat)
RCT_EXPORT_VIEW_PROPERTY(strokeLinecap, CGLineCap)
RCT_EXPORT_VIEW_PROPERTY(strokeLinejoin, CGLineJoin)
RCT_EXPORT_VIEW_PROPERTY(clipPath, CGPath)
RCT_EXPORT_VIEW_PROPERTY(clipRule, RNSVGCGFCRule)
RCT_EXPORT_VIEW_PROPERTY(strokeDasharray, RNSVGCGFloatArray)
RCT_EXPORT_VIEW_PROPERTY(strokeDashoffset, CGFloat)
@end

Просмотреть файл

@ -20,7 +20,10 @@ RCT_EXPORT_MODULE()
return [RNSVGImage new];
}
RCT_EXPORT_VIEW_PROPERTY(layout, NSDictionary)
RCT_EXPORT_VIEW_PROPERTY(x, NSString)
RCT_EXPORT_VIEW_PROPERTY(y, NSString)
RCT_EXPORT_VIEW_PROPERTY(width, NSString)
RCT_EXPORT_VIEW_PROPERTY(height, NSString)
RCT_EXPORT_VIEW_PROPERTY(src, id)
@end

Просмотреть файл

@ -0,0 +1,13 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGRenderableManager.h"
@interface RNSVGLineManager : RNSVGRenderableManager
@end

Просмотреть файл

@ -0,0 +1,40 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGLineManager.h"
#import "RNSVGLine.h"
#import "RCTConvert+RNSVG.h"
@implementation RNSVGLineManager
RCT_EXPORT_MODULE()
- (RNSVGRenderable *)node
{
return [RNSVGLine new];
}
RCT_EXPORT_VIEW_PROPERTY(x1, NSString)
RCT_EXPORT_VIEW_PROPERTY(y1, NSString)
RCT_EXPORT_VIEW_PROPERTY(x2, NSString)
RCT_EXPORT_VIEW_PROPERTY(y2, NSString)
// fix me: these should inherited from renderable
RCT_EXPORT_VIEW_PROPERTY(fill, RNSVGBrush)
RCT_EXPORT_VIEW_PROPERTY(fillRule, RNSVGCGFCRule)
RCT_EXPORT_VIEW_PROPERTY(stroke, RNSVGBrush)
RCT_EXPORT_VIEW_PROPERTY(strokeWidth, CGFloat)
RCT_EXPORT_VIEW_PROPERTY(strokeLinecap, CGLineCap)
RCT_EXPORT_VIEW_PROPERTY(strokeLinejoin, CGLineJoin)
RCT_EXPORT_VIEW_PROPERTY(clipPath, CGPath)
RCT_EXPORT_VIEW_PROPERTY(clipRule, RNSVGCGFCRule)
RCT_EXPORT_VIEW_PROPERTY(strokeDasharray, RNSVGCGFloatArray)
RCT_EXPORT_VIEW_PROPERTY(strokeDashoffset, CGFloat)
@end

Просмотреть файл

@ -16,17 +16,17 @@ RCT_EXPORT_MODULE()
- (RNSVGNode *)node
{
return [RNSVGNode new];
return [RNSVGNode new];
}
- (UIView *)view
{
return [self node];
return [self node];
}
- (RCTShadowView *)shadowView
{
return nil;
return nil;
}
RCT_EXPORT_VIEW_PROPERTY(opacity, CGFloat)

Просмотреть файл

@ -0,0 +1,13 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGRenderableManager.h"
@interface RNSVGRectManager : RNSVGRenderableManager
@end

Просмотреть файл

@ -0,0 +1,42 @@
/**
* Copyright (c) 2015-present, Horcrux.
* All rights reserved.
*
* This source code is licensed under the MIT-style license found in the
* LICENSE file in the root directory of this source tree.
*/
#import "RNSVGRectManager.h"
#import "RNSVGRect.h"
#import "RCTConvert+RNSVG.h"
@implementation RNSVGRectManager
RCT_EXPORT_MODULE()
- (RNSVGRenderable *)node
{
return [RNSVGRect new];
}
RCT_EXPORT_VIEW_PROPERTY(x, NSString)
RCT_EXPORT_VIEW_PROPERTY(y, NSString)
RCT_EXPORT_VIEW_PROPERTY(width, NSString)
RCT_EXPORT_VIEW_PROPERTY(height, NSString)
RCT_EXPORT_VIEW_PROPERTY(rx, NSString)
RCT_EXPORT_VIEW_PROPERTY(ry, NSString)
// fix me: these should inherited from renderable
RCT_EXPORT_VIEW_PROPERTY(fill, RNSVGBrush)
RCT_EXPORT_VIEW_PROPERTY(fillRule, RNSVGCGFCRule)
RCT_EXPORT_VIEW_PROPERTY(stroke, RNSVGBrush)
RCT_EXPORT_VIEW_PROPERTY(strokeWidth, CGFloat)
RCT_EXPORT_VIEW_PROPERTY(strokeLinecap, CGLineCap)
RCT_EXPORT_VIEW_PROPERTY(strokeLinejoin, CGLineJoin)
RCT_EXPORT_VIEW_PROPERTY(clipPath, CGPath)
RCT_EXPORT_VIEW_PROPERTY(clipRule, RNSVGCGFCRule)
RCT_EXPORT_VIEW_PROPERTY(strokeDasharray, RNSVGCGFloatArray)
RCT_EXPORT_VIEW_PROPERTY(strokeDashoffset, CGFloat)
@end

Просмотреть файл

@ -17,7 +17,7 @@ RCT_EXPORT_MODULE()
- (RNSVGRenderable *)node
{
return [RNSVGShape new];
return [RNSVGShape new];
}
RCT_EXPORT_VIEW_PROPERTY(shape, NSDictionary)

Просмотреть файл

@ -7,7 +7,6 @@
*/
#import "RNSVGSvgViewManager.h"
#import "RNSVGSvgView.h"
@implementation RNSVGSvgViewManager

Просмотреть файл

@ -24,4 +24,6 @@ RCT_EXPORT_VIEW_PROPERTY(alignment, CTTextAlignment)
RCT_REMAP_VIEW_PROPERTY(frame, textFrame, RNSVGTextFrame)
RCT_EXPORT_VIEW_PROPERTY(path, CGPath)
@end

42
lib/SvgTouchableMixin.js Normal file
Просмотреть файл

@ -0,0 +1,42 @@
import Touchable from 'react-native/Libraries/Components/Touchable/Touchable';
const PRESS_RETENTION_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
export default {
...Touchable.Mixin,
touchableHandlePress: function(e) {
this.props.onPress && this.props.onPress(e);
},
touchableHandleActivePressIn: function(e) {
this.props.onPressIn && this.props.onPressIn(e);
},
touchableHandleActivePressOut: function(e) {
this.props.onPressOut && this.props.onPressOut(e);
},
touchableHandleLongPress: function(e) {
this.props.onLongPress && this.props.onLongPress(e);
},
touchableGetPressRectOffset: function() {
return this.props.pressRetentionOffset || PRESS_RETENTION_OFFSET;
},
touchableGetHitSlop: function() {
return this.props.hitSlop;
},
touchableGetHighlightDelayMS: function() {
return this.props.delayPressIn || 0;
},
touchableGetLongPressDelayMS: function() {
return this.props.delayLongPress === 0 ? 0 :
this.props.delayLongPress || 500;
},
touchableGetPressOutDelayMS: function() {
return this.props.delayPressOut || 0;
}
}

Просмотреть файл

@ -1,9 +1,11 @@
import _ from 'lodash';
import ReactNativeViewAttributes from 'react-native/Libraries/Components/View/ReactNativeViewAttributes';
function arrayDiffer(a, b) {
if (_.isNil(a)) {
return true;
}
if (a.length !== b.length) {
return true;
}
@ -57,6 +59,7 @@ function fontAndLinesDiffer(a, b) {
}
const NodeAttributes = {
...ReactNativeViewAttributes.UIView,
transform: {
diff: arrayDiffer
},

Просмотреть файл

@ -2,14 +2,16 @@ import extractFill from './extractFill';
import extractStroke from './extractStroke';
import extractTransform from './extractTransform';
import extractClipping from './extractClipping';
import extractResponder from './extractResponder';
import _ from 'lodash';
export default function(props, options = {stroke: true, transform: true, fill: true}) {
export default function(props, options = {stroke: true, transform: true, fill: true, responder: true}) {
if (props.visible === false) {
return {
opacity: 0
};
}
let extractedProps = {
opacity: +props.opacity || 1
};
@ -30,5 +32,9 @@ export default function(props, options = {stroke: true, transform: true, fill: t
extractedProps.transform = extractTransform(props);
}
if (options.responder) {
_.assign(extractedProps, extractResponder(props));
}
return extractedProps;
}

Просмотреть файл

@ -0,0 +1,6 @@
import {responderPropsKeys} from '../props';
import _ from 'lodash';
export default function (props) {
return _.pick(props, responderPropsKeys);
}

11
lib/mergeContext.js Normal file
Просмотреть файл

@ -0,0 +1,11 @@
import _ from 'lodash';
export default function (props, context) {
if (context.isInGroup) {
props = _.defaults({}, props, context, {
isInGroup: null
});
}
return props;
}

Просмотреть файл

@ -1,7 +1,32 @@
import {PropTypes} from 'react';
import {PanResponder} from 'react-native';
const numberProp = PropTypes.oneOfType([PropTypes.string, PropTypes.number]);
const touchableProps = {
disabled: PropTypes.bool,
onPress: PropTypes.func,
onPressIn: PropTypes.func,
onPressOut: PropTypes.func,
onLongPress: PropTypes.func,
delayPressIn: PropTypes.number,
delayPressOut: PropTypes.number,
delayLongPress: PropTypes.number
};
const touchablePropsKeys = Object.keys(touchableProps);
const responderPropsKeys = [
...Object.keys(PanResponder.create({onStartShouldSetPanResponder: () => {}}).panHandlers),
'pointerEvents'
];
const responderProps = responderPropsKeys.reduce((props, name) => {
props[name] = PropTypes.func;
return props;
}, {});
const fillProps = {
fill: PropTypes.string,
fillOpacity: numberProp,
@ -50,7 +75,8 @@ const pathProps = {
...fillProps,
...strokeProps,
...clipProps,
...transformProps
...transformProps,
...responderProps
};
const circleProps = {
@ -104,5 +130,9 @@ export {
lineProps,
rectProps,
contextProps,
pathProps
pathProps,
responderProps,
responderPropsKeys,
touchableProps,
touchablePropsKeys
};