0

私は、特にノードとエッジを持つスクロールビューを含むiosアプリに取り組んでいます。

最初はcalayerを使用し、開始ノードと終了ノードを監視するキー値を使用しました。次のコードを使用して、エッジとエッジ ラベルを描画します。

- (void)drawInContext:(CGContextRef)ctx
{
CGContextSetStrokeColorWithColor(ctx, [UIColor blackColor].CGColor);
CGContextSetLineWidth(ctx, 2);
CGContextMoveToPoint(ctx, _startNode.center.x, _startNode.center.y);
CGContextAddLineToPoint(ctx, _endNode.center.x, _endNode.center.y);

CGContextStrokePath(ctx);
CGContextSetFillColorWithColor(ctx, [[UIColor darkTextColor] CGColor]);

UIGraphicsPushContext(ctx);

CGContextSaveGState(ctx);
CGRect rect = CGRectMake(((_startNode.center.x + _endNode.center.x)/2)-50, ((_startNode.center.y + _endNode.center.y)/2)-15, 100, 30);

CGFloat angle = atan2f(_endNode.center.y - _startNode.center.y, _endNode.center.x - _startNode.center.x) * 180 / PI;
CGAffineTransform transform = CGAffineTransformIdentity;
transform = CGAffineTransformTranslate(transform, CGRectGetMidX(rect), CGRectGetMidY(rect));
transform = CGAffineTransformRotate(transform, angle * M_PI/180.0);
transform = CGAffineTransformTranslate(transform, -CGRectGetMidX(rect), -CGRectGetMidY(rect));
CGContextConcatCTM(ctx, transform);
NSMutableParagraphStyle* p = [NSMutableParagraphStyle new];
p.alignment = NSTextAlignmentCenter;
UIFont *font = [UIFont fontWithName:@"Helvetica" size:12];
NSMutableDictionary *attributes = [[NSMutableDictionary alloc] init];
[attributes setObject:font forKey:NSFontAttributeName];
[attributes setObject:[UIColor blackColor] forKey:NSForegroundColorAttributeName];
[attributes setObject:p forKey:NSParagraphStyleAttributeName];
[_edgeName drawInRect:rect withAttributes:attributes];
CGContextRestoreGState(ctx);


UIGraphicsPopContext();
}

これは機能し、ノードをドラッグしてエッジをたどることができましたが、メモリの問題によりアプリがクラッシュしました。すると、代わりにcashapelayerを使うべきだと言われました。これもかなりうまく機能しますが、エッジにラベルを追加する際に問題が発生しました。

ラベルは、エッジの中心に合わせて配置および回転する必要があります。

次のコードは、cashapelayer としてエッジを描画する方法を示しています

@implementation EdgeShape

#define PI 3.14159265
- (id)init {
self = [super init];
if (self) {

}
return self;
}

- (void)setStartNode:(UIView *)startNode
{
[startNode addObserver:self forKeyPath:@"center" options:NSKeyValueObservingOptionNew context:nil];
[startNode addObserver:self forKeyPath:@"hidden" options:NSKeyValueObservingOptionNew context:nil];
_startNode = startNode;
[self drawPath];
}

- (void)setEndNode:(UIView *)endNode
{
[endNode addObserver:self forKeyPath:@"center" options:NSKeyValueObservingOptionNew context:nil];
[endNode addObserver:self forKeyPath:@"hidden" options:NSKeyValueObservingOptionNew context:nil];
_endNode = endNode;
[self drawPath];
}


-(void) observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context
{
if ([keyPath isEqualToString:@"center"] )
{
    [self drawPath];
}
if([keyPath isEqualToString:@"hidden"]){

    [self removeFromSuperlayer];

}
}

- (void) drawPath{
CGMutablePathRef cgPath = CGPathCreateMutable();
CGPathMoveToPoint(cgPath , NULL, _startNode.center.x, _startNode.center.y);
CGPathAddLineToPoint(cgPath , NULL, _endNode.center.x, _endNode.center.y);
NSLog(@"shape x : %f", _startNode.center.x);
self.lineWidth = 2.0f;
self.strokeColor = [UIColor blackColor].CGColor;
self.fillColor = [UIColor clearColor].CGColor;
self.path = cgPath;
}

@end

catextlayer を追加するにはどうすればよいですか? キャサペレイヤーのサブレイヤーとして、またはスクロールビューのサブレイヤーとして?

ノードの変更にオブザーバーを使用して catextlayer を追加しようとしましたが、cashapelayer と同時に更新することはできません。

ご理解いただければ幸いです。そうでない場合は、教えてください。問題を明確にするよう努めます。

ありがとう。

4

1 に答える 1

0

次の行をobserveValueForKeyPathに追加して、問題を解決しました。私が理解している限り、これにより catextlayers の位置を更新するときにアニメーションが削除されます。少なくとも catextlayer は遅滞なく cashapelayer に従います。

if ([keyPath isEqualToString:@"center"] )
{
    [CATransaction begin];
    [CATransaction setValue:(id)kCFBooleanTrue forKey:kCATransactionDisableActions];
    _textLayer.position = CGPointMake((_startNode.center.x + _endNode.center.x)/2, (_startNode.center.y + _endNode.center.y)/2);
    CGFloat angle = atan2f(_endNode.center.y - _startNode.center.y, _endNode.center.x - _startNode.center.x) * 180 / PI;
    _textLayer.transform = CATransform3DMakeAffineTransform(CGAffineTransformMakeRotation(angle * M_PI/180.0));
    [CATransaction commit];
    [self drawPath];
}
于 2014-06-20T00:47:50.657 に答える