diff --git a/pxSVG-TestApp/ViewController.m b/pxSVG-TestApp/ViewController.m index 0c508ad..f819ae4 100644 --- a/pxSVG-TestApp/ViewController.m +++ b/pxSVG-TestApp/ViewController.m @@ -19,6 +19,7 @@ @implementation SVGCollectionCell - (instancetype)initWithFrame:(CGRect)frame { self = [super initWithFrame:frame]; + self.backgroundColor = [UIColor whiteColor]; pxSVGView *sv = [[pxSVGView alloc] initWithFrame:self.contentView.bounds]; sv.svgDelegate = self; sv.autoresizingMask = UIViewAutoresizingFlexibleWidth|UIViewAutoresizingFlexibleHeight; @@ -54,10 +55,10 @@ @implementation ViewController - (instancetype)init { UICollectionViewFlowLayout *layout = [UICollectionViewFlowLayout new]; - layout.itemSize = (CGSize){160,160}; + layout.itemSize = (CGSize){159,159}; layout.sectionInset = UIEdgeInsetsZero; - layout.minimumInteritemSpacing = 0; - layout.minimumLineSpacing = 0; + layout.minimumInteritemSpacing = 1; + layout.minimumLineSpacing = 1; layout.scrollDirection = UICollectionViewScrollDirectionVertical; self = [super initWithCollectionViewLayout:layout]; self.images = [NSBundle URLsForResourcesWithExtension:@"svg" subdirectory:nil inBundleWithURL:[NSBundle mainBundle].bundleURL]; @@ -67,7 +68,7 @@ - (instancetype)init - (void)viewDidLoad { [super viewDidLoad]; - self.collectionView.backgroundColor = [UIColor whiteColor]; + self.collectionView.backgroundColor = [UIColor grayColor]; [self.collectionView registerClass:[SVGCollectionCell class] forCellWithReuseIdentifier:@"cell"]; } diff --git a/pxSVG/pxSVGLayer.h b/pxSVG/pxSVGLayer.h index 8288373..5def575 100644 --- a/pxSVG/pxSVGLayer.h +++ b/pxSVG/pxSVGLayer.h @@ -20,5 +20,5 @@ - (void) loadData:(NSData*)data; - (void) loadString:(NSString*)string; - (void) loadURL:(NSURL*)url; -@property (nonatomic,readonly) CGRect contentRect; +@property (readonly) CGRect contentRect; @end diff --git a/pxSVG/pxSVGLayer.m b/pxSVG/pxSVGLayer.m index cd347bc..41ed6b7 100644 --- a/pxSVG/pxSVGLayer.m +++ b/pxSVG/pxSVGLayer.m @@ -12,6 +12,7 @@ @interface pxSVGLayer () @property NSOperation *loadOperation; @property NSOperation *parseOperation; +@property CGRect contentRect; @end @implementation pxSVGLayer @@ -103,6 +104,7 @@ - (void)loadImage:(pxSVGImage*)image { [self clean]; [self addSublayer:[image makeLayer]]; + self.contentRect = image.bounds; if ([self.svgDelegate respondsToSelector:@selector(svgLayerDidLoadImage:)]) [self.svgDelegate svgLayerDidLoadImage:self]; } @@ -118,15 +120,7 @@ - (void)clean if (self.loadOperation) [self.loadOperation cancel]; if (self.parseOperation) [self.parseOperation cancel]; while (self.sublayers.count) [self.sublayers.firstObject removeFromSuperlayer]; -} - -- (CGRect)contentRect -{ - CGRect f = CGRectNull; - for (CALayer *l in self.sublayers) { - f = CGRectUnion(f, l.frame); - } - return f; + self.contentRect = CGRectZero; } @end diff --git a/pxSVG/pxSVGObject.m b/pxSVG/pxSVGObject.m index 039eebf..a37dc19 100644 --- a/pxSVG/pxSVGObject.m +++ b/pxSVG/pxSVGObject.m @@ -36,9 +36,6 @@ + (CATransform3D) transformFromString:(NSString*)string } } else if ([op isEqualToString:@"translate"]) { switch (i) { - case 1: - tr = CATransform3DTranslate(tr, p[0], 0, 0); - break; case 2: tr = CATransform3DTranslate(tr, p[0], p[1], 0); break; diff --git a/pxSVG/pxSVGRenderPath.m b/pxSVG/pxSVGRenderPath.m index d00ec59..150a55d 100644 --- a/pxSVG/pxSVGRenderPath.m +++ b/pxSVG/pxSVGRenderPath.m @@ -25,7 +25,18 @@ - (instancetype)initWithXML:(pxXMLNode *)xmlNode { self = [super init]; self.root = [self parseObject:xmlNode inheritAttributes:nil]; - if ([xmlNode.attributes objectForKey:@"width"] && + if ([xmlNode.attributes objectForKey:@"viewBox"]) { + NSArray *vb = [[xmlNode.attributes objectForKey:@"viewBox"] componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceCharacterSet]]; + self.bounds = (CGRect){ + { + [vb[0] doubleValue], + [vb[1] doubleValue] + },{ + [vb[2] doubleValue], + [vb[3] doubleValue] + } + }; + } else if ([xmlNode.attributes objectForKey:@"width"] && [xmlNode.attributes objectForKey:@"height"]) { CGPoint o = CGPointZero; if ([xmlNode.attributes objectForKey:@"x"] && @@ -41,17 +52,6 @@ - (instancetype)initWithXML:(pxXMLNode *)xmlNode [[xmlNode.attributes objectForKey:@"height"] doubleValue] } }; - } else if ([xmlNode.attributes objectForKey:@"viewBox"]) { - NSArray *vb = [[xmlNode.attributes objectForKey:@"viewBox"] componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceCharacterSet]]; - self.bounds = (CGRect){ - { - [vb[0] doubleValue], - [vb[1] doubleValue] - },{ - [vb[2] doubleValue], - [vb[3] doubleValue] - } - }; } else { self.bounds = [self objBounds:self.root]; } @@ -112,17 +112,12 @@ - (pxSVGObject*)parseObject:(pxXMLNode*)node inheritAttributes:(pxSVGObject*)inh } return obj; } -- (CALayer *)makeLayerWithNode:(pxSVGObject*)node withOffset:(CGPoint)off +- (CALayer *)makeLayerWithNode:(pxSVGObject*)node { - CGRect f = [self objBounds:node]; - if (CGRectIsNull(f)) return nil; CALayer *l; if ([node respondsToSelector:@selector(d)]) { CAShapeLayer *sl = [CAShapeLayer new]; - CGAffineTransform t = CGAffineTransformMakeTranslation(-f.origin.x, -f.origin.y); - CGPathRef p = CGPathCreateCopyByTransformingPath([(id)node d].CGPath, &t); - sl.path = p; - CGPathRelease(p); + sl.path = [(id)node d].CGPath; sl.fillColor = (node.fillColor?:[UIColor blackColor]).CGColor; sl.strokeColor = node.strokeColor.CGColor; sl.lineWidth = node.strokeWidth==NAN?0:node.strokeWidth; @@ -130,12 +125,15 @@ - (CALayer *)makeLayerWithNode:(pxSVGObject*)node withOffset:(CGPoint)off } else { l = [CALayer new]; } - l.frame = CGRectOffset(f, -off.x, -off.y); - l.transform = node.transform; + l.frame = self.bounds; + CATransform3D tr = node.transform; + tr = CATransform3DConcat(CATransform3DMakeTranslation(-self.bounds.size.width/2, self.bounds.size.height/2, 0), tr); + tr = CATransform3DConcat(tr, CATransform3DMakeTranslation( self.bounds.size.width/2, -self.bounds.size.height/2, 0)); + l.transform = tr; l.opacity = node.opacity; if ([node respondsToSelector:@selector(subnodes)]) { for (pxSVGObject *n in [(id)node subnodes]) { - CALayer *sl = [self makeLayerWithNode:n withOffset:(CGPoint){f.origin.x+off.x,f.origin.y+off.y}]; + CALayer *sl = [self makeLayerWithNode:n]; if (sl) [l addSublayer:sl]; } } @@ -143,6 +141,6 @@ - (CALayer *)makeLayerWithNode:(pxSVGObject*)node withOffset:(CGPoint)off } - (CALayer *)makeLayer { - return [self makeLayerWithNode:self.root withOffset:CGPointZero]; + return [self makeLayerWithNode:self.root]; } @end diff --git a/pxSVG/pxSVGView.m b/pxSVG/pxSVGView.m index 8a47f6b..ca55e3f 100644 --- a/pxSVG/pxSVGView.m +++ b/pxSVG/pxSVGView.m @@ -29,13 +29,10 @@ - (instancetype)initWithFrame:(CGRect)frame - (void)layoutSublayersOfLayer:(CALayer *)layer { if (layer != self.layer) return; + self.svgLayer.transform = CATransform3DIdentity; [self.svgLayer setFrame:self.layer.bounds]; -} - -- (void)svgLayerDidLoadImage:(pxSVGLayer *)svgLayer -{ CATransform3D tr = CATransform3DIdentity; - CGRect c = svgLayer.contentRect; + CGRect c = self.svgLayer.contentRect; switch (self.contentMode) { case UIViewContentModeScaleAspectFit: { CGFloat @@ -43,12 +40,19 @@ - (void)svgLayerDidLoadImage:(pxSVGLayer *)svgLayer scy = c.size.height/self.bounds.size.height, sc = MAX(scx,scy); tr = CATransform3DMakeScale(1/sc, 1/sc, 1); - tr = CATransform3DTranslate(tr, -c.origin.x/sc, -c.origin.y/sc, 0); + tr = CATransform3DTranslate(tr, -c.size.width/2, -c.size.height/2, 0); + tr = CATransform3DTranslate(tr, self.bounds.size.width/2, self.bounds.size.height/2, 0); break; } default: break; } - [svgLayer setTransform:tr]; + [self.svgLayer setTransform:tr]; +} + +- (void)svgLayerDidLoadImage:(pxSVGLayer *)svgLayer +{ + [self setNeedsLayout]; + [self setNeedsDisplay]; if ([self.svgDelegate respondsToSelector:@selector(svgViewDidLoadImage:)]) [self.svgDelegate svgViewDidLoadImage:self]; }