2017-09-07 2 views
0

Three Controllers only first two pressed여러 개의 하위 클래스 UIView 개체를 동시에 그릴 수 없습니다. 시도 많은 방법

은 [편집]

원래 질문은 아래 시작합니다. 추가 정보가 있습니다

저는 하루 종일이 문제를 해결해 왔으며 해결 방법을 찾을 수 없습니다. UIView 하위 클래스 및 드로잉 코드를 다음 줄입니다.

-(void)drawRect:(CGRect)rect 
{ 


    //// rechargeLevel Drawing 
    CGRect rechargeLevelRect = CGRectMake(17.5, 17.75, 64, 64); 
    UIBezierPath* rechargeLevelPath = [UIBezierPath bezierPath]; 
    [rechargeLevelPath addArcWithCenter: CGPointMake(CGRectGetMidX(rechargeLevelRect), CGRectGetMidY(rechargeLevelRect)) radius: rechargeLevelRect.size.width/2 startAngle: 90 * M_PI/180 endAngle: endAngle * M_PI/180 clockwise: YES]; 

    [[UIColor redColor] setStroke]; 
    rechargeLevelPath.lineWidth = 4.5; 
    [rechargeLevelPath stroke]; 

    endAngle++; 
    if (endAngle > 359) { 
     endAngle = 1; 
    } 
} 

나는 다음 모든 것을 시도했다.

  1. 의 drawRect : setNeedsDisplay를 호출 타이머 (또한 시도 setNeedsDisplayInRect : 후 호출 블록 내부 형상을

  2. CAShapeLayer를 그리는 방법을 호출하는 타이머

  3. CAShapeLayer 타이머가 일을 망쳐 놓고있는 것 같아서.

  4. 동일한 코드이지만 diff가있는 UIView의 두 번째 하위 클래스를 만들었습니다. e 라벨. 초기화 중 하나가 여전히 작동하지 않습니다.

  5. 두 가지 하위 클래스간에 위의 방법을 조합하여 사용해 보았습니다.

동일한 컨텍스트를 사용하여 다른 타이머를 시작하거나 타이머를 시작할 때 타이머가 멈 춥니 다. 나는 모른다.

내가 만든 테스트 프로젝트로 GitHub 저장소를 만들었습니다. 여기에는 두 개의 하위 클래스에서 위 메소드를 각각 초기화하고 뷰에 추가하는 6 개의 버튼이있는 viewController가 있습니다.

GitHub의의의 repo는 다음과 같습니다 https://github.com/MoseCode/drawTest

[최종 편집]

원래의 질문은 다음과 같습니다

동시에 여러 개체에 타이머 그리기 사용자 정의의 drawRect을하려고합니다.

터치 이벤트를 수신하도록 설정된 사용자 지정 UIController (WP_BonusController)가 있습니다. 컨트롤러를 5 번 터치하면 지정된 시간이 경과 할 때까지 이벤트가 비활성화됩니다.

재충전 시간을 설명하기 위해 DrawRect에서 원 경로를 그립니다. UIGraphicsGetCurrentContext 사용하고 다음 새 경로를 쓰다듬어.

내 문제는 UIGraphicsGetCurrentContext에서 동일한 컨텍스트를 공유하는 WP_BonusController 개체를 여러 인스턴스로 인스턴스화 할 때 발생합니다. 나는 물체에 대한 램 할당을 확인했는데 모두 다르다. 그러나 drawRect에 중단 점을 넣을 때 CGContextRef를 UIGraphicsGetCurrentContext에서 확인하면 모두 동일한 RAM 할당을가집니다.

bonusController1을 다섯 번 누르면 타이머가 시작되고 아이콘 주위에 원을 그리기 시작합니다. 그것은 잘 작동합니다.

그런 다음 bonusController2를 다섯 번 누르고 타이머를 시작하지만 drawRect에서 컨텍스트를 그릴 때 나는 다른 bonusController1에서 동일한 컨텍스트를 얻습니다. 따라서 그려지는 선은 이미 절반이 그려져 있습니다.

이것은 모든 컨트롤러에서 동일합니다.

UIGraphicsGetCurrentContext를 사용하지 않는 깨끗한 컨텍스트를 만들 수있는 방법이 있습니까? 나는 모든 것을 조사해 왔으며 해결책을 찾을 수 없다. 어쩌면 문맥의 사용법을 정확하게 이해하지 못할 수도 있습니다. 나는이 컨트롤러를 언제든지 여러 번 개별적으로 그릴 수 있어야합니다. 타이머에 의해 호출됩니다 :

-(void)drawRect:(CGRect)rect 
{ 
    _currentAngle = _currentAngle + 1; 

    UIGraphicsBeginImageContextWithOptions(CGSizeMake(self.frame.size.width, self.frame.size.height), NO, 0); 


    // General Declarations 
    CGContextRef context = UIGraphicsGetCurrentContext(); 
    // Resize to Target Frame 
    CGContextSaveGState(context); 
    CGRect resizedFrame = WP_CustomIconsResizingBehaviorApply(WP_CustomIconsResizingBehaviorAspectFill, CGRectMake(0, 0, 100, 100), [self getImageRect]); 
    CGContextTranslateCTM(context, resizedFrame.origin.x, resizedFrame.origin.y); 
    CGContextScaleCTM(context, resizedFrame.size.width/100, resizedFrame.size.height/100); 


    //// rechargeLevel Drawing 
    CGRect rechargeLevelRect = CGRectMake(17.5, 17.75, 64, 64); 
    UIBezierPath* rechargeLevelPath = [UIBezierPath bezierPath]; 
    [rechargeLevelPath addArcWithCenter: CGPointMake(CGRectGetMidX(rechargeLevelRect), CGRectGetMidY(rechargeLevelRect)) radius: rechargeLevelRect.size.width/2 startAngle: 90 * M_PI/180 endAngle: _currentAngle * M_PI/180 clockwise: YES]; 

    [WP_CustomIcons.thirdColor setStroke]; 
    rechargeLevelPath.lineWidth = 4.5; 
    [rechargeLevelPath stroke]; 
    CGContextRestoreGState(context); 

    refillMeter = UIGraphicsGetImageFromCurrentImageContext(); 
    UIGraphicsEndImageContext(); 

    [self.refillImageView setImage:refillMeter]; 

} 
+1

이 그리기 방법은 사용자 정의 UIView의 구현에 속해? –

+0

예 Reinier, 일종의 사용자 지정 UIView입니다. 그것은 UIControl의 하위 클래스이며 UIView의 하위 클래스이며 괜찮을 것이라고 생각했습니다. 나는이 일의 다른 구현을 시도하면서 그들의 일을 할 수 없게 만들었습니다. 그 밖의 다른 것을 시도하면서 내 질문을 업데이트 할 것입니다. 고맙습니다. –

+0

금요일부터 Irma 허리케인으로 인해 죄송합니다. 그래서 당신이 건배를 처리 할 수 ​​있다는 것을 알았습니다! –

답변

0

이 그것을 알아 냈

여기 내의 drawRect입니다. 마지막으로 시도해보십시오. 어쩌면 처음이었을 것입니다. 그러나 저는 타이머에 대해서 생각하고있었습니다.

CALayerAnimation

@implementation ThirdTimerView 


- (id)initWithFrame:(CGRect)frame 
{ 
    self = [super initWithFrame:frame]; 
    if (self) { 
     // 
    } 
    return self; 
} 

-(UIBezierPath *)samplePath 
{ 
    CGRect rechargeLevelRect = CGRectMake(17.5, 17.75, 64, 64); 
    UIBezierPath* rechargeLevelPath = [UIBezierPath bezierPath]; 
    [rechargeLevelPath addArcWithCenter: CGPointMake(CGRectGetMidX(rechargeLevelRect), CGRectGetMidY(rechargeLevelRect)) radius: rechargeLevelRect.size.width/2 startAngle: 90 * M_PI/180 endAngle: 450 * M_PI/180 clockwise: YES]; 

    return rechargeLevelPath; 
} 


- (void)startAnimation 
{ 
    if (self.pathLayer == nil) 
    { 
     CAShapeLayer *shapeLayer = [CAShapeLayer layer]; 

     shapeLayer.path = [[self samplePath] CGPath]; 
     shapeLayer.strokeColor = [[UIColor redColor] CGColor]; 
     shapeLayer.fillColor = nil; 
     shapeLayer.lineWidth = 4.5f; 
     shapeLayer.lineJoin = kCALineJoinBevel; 

     [self.layer addSublayer:shapeLayer]; 

     self.pathLayer = shapeLayer; 
    } 

    CABasicAnimation *pathAnimation = [CABasicAnimation animationWithKeyPath:@"strokeTimer"]; 
    pathAnimation.duration = 3.0; 
    pathAnimation.fromValue = @(0.0f); 
    pathAnimation.toValue = @(1.0f); 

    [CATransaction setCompletionBlock:^{ 

     [self removeFromSuperview]; 

    }]; 

    [self.pathLayer addAnimation:pathAnimation forKey:@"strokeTimer"]; 
} 

@end 
관련 문제