2013-12-17 4 views
1

Я разрабатываю пользовательский круговой индикатор выполнения, используя UIBezierPath. Я хочу изменить прогресс, основанный на случайно генерируемых значениях CGFloat.Re-draw UIBezierPath на основе случайного значения CGFloat

Мой прогресс бар выглядит следующим образом:

enter image description here

Я обратил индикатор, используя следующий код:

// Draw the arc with bezier path 
    int radius = 100; 

    CAShapeLayer *arc = [CAShapeLayer layer]; 
    arc.path = [UIBezierPath bezierPathWithArcCenter:CGPointMake(100, 50) radius:radius startAngle:M_PI endAngle:M_PI/150 clockwise:YES].CGPath; 
    arc.position = CGPointMake(CGRectGetMidX(self.view.frame)-radius, 
           CGRectGetMidY(self.view.frame)-radius); 
    arc.cornerRadius = 100.0; 
    arc.fillColor = [UIColor clearColor].CGColor; 
    arc.strokeColor = [UIColor purpleColor].CGColor; 
    arc.lineWidth = 6; 

    [self.view.layer addSublayer:arc]; 

    // Animation of the progress bar 
    CABasicAnimation *drawAnimation = [CABasicAnimation animationWithKeyPath:@"strokeEnd"]; 
    drawAnimation.duration   = 5.0; // "animate over 10 seconds or so.." 
    drawAnimation.repeatCount   = 1.0; // Animate only once.. 
    drawAnimation.removedOnCompletion = YES; // Remain stroked after the animation.. 
    drawAnimation.fromValue = [NSNumber numberWithFloat:0.0f]; 
    drawAnimation.toValue = [NSNumber numberWithFloat:10.0f]; 
    drawAnimation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseIn]; 
    [arc addAnimation:drawAnimation forKey:@"drawCircleAnimation"]; 

    // Gradient of progress bar 
    CAGradientLayer *gradientLayer = [CAGradientLayer layer]; 
    gradientLayer.frame = self.view.frame; 
    gradientLayer.colors = @[(__bridge id)[UIColor redColor].CGColor,(__bridge id)[UIColor yellowColor].CGColor,(__bridge id)[UIColor purpleColor].CGColor ]; 
    gradientLayer.startPoint = CGPointMake(0,0.1); 
    gradientLayer.endPoint = CGPointMake(0.5,0.2); 
    [self.view.layer addSublayer:gradientLayer]; 
    gradientLayer.mask = arc; 

    refreshButton = [[UIButton alloc] initWithFrame:CGRectMake(50, 370, 50, 50)]; 
    [refreshButton addTarget:self action:@selector(refresh:) forControlEvents:UIControlEventTouchUpInside]; 
    [refreshButton setBackgroundImage:[UIImage imageNamed:@"refresh.png"] forState:UIControlStateNormal]; 
    [self.view addSubview:refreshButton]; 

UIButton с зеленой стрелкой генерирует случайным образом значения CGFloat. Итак, мой вопрос заключается в том, как сбросить анимацию, чтобы она остановилась в соответствующей позиции, если она находится между 0.0 и 1.0? Я попытался вставить код для анимации внутри метода кнопки, но в результате новая дуга была нарисована поверх существующей.

-(void)refresh:(id)sender{ 
    NSLog(@"Refresh action:"); 
    CGFloat randomValue = (arc4random() % 256/256.0); 
    NSLog(@"%f", randomValue); 

    valueLabel.text = @""; 
    valueLabel = [[UILabel alloc] initWithFrame:CGRectMake(150, 370, 100, 50)]; 
    valueLabel.text = [NSString stringWithFormat: @"%.6f", randomValue]; 
    [self.view addSubview:valueLabel]; 

    // Draw the arc with bezier path 
    int radius = 100; 

    CAShapeLayer *arc = [CAShapeLayer layer]; 
    arc.path = [UIBezierPath bezierPathWithArcCenter:CGPointMake(100, 50) radius:radius startAngle:M_PI endAngle:M_PI/150 clockwise:YES].CGPath; 
    arc.position = CGPointMake(CGRectGetMidX(self.view.frame)-radius, 
           CGRectGetMidY(self.view.frame)-radius); 
    arc.cornerRadius = 100.0; 
    arc.fillColor = [UIColor clearColor].CGColor; 
    arc.strokeColor = [UIColor purpleColor].CGColor; 
    arc.lineWidth = 6; 

    [self.view.layer addSublayer:arc]; 

    // Animation of the progress bar 
    CABasicAnimation *drawAnimation = [CABasicAnimation animationWithKeyPath:@"strokeEnd"]; 
    drawAnimation.duration   = 5.0; // "animate over 10 seconds or so.." 
    drawAnimation.repeatCount   = 1.0; // Animate only once.. 
    drawAnimation.removedOnCompletion = YES; // Remain stroked after the animation.. 
    drawAnimation.fromValue = [NSNumber numberWithFloat:0.0f]; 
    drawAnimation.toValue = [NSNumber numberWithFloat:randomValue]; 
    drawAnimation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseIn]; 
    [arc addAnimation:drawAnimation forKey:@"drawCircleAnimation"]; 


} 

Я не имею понятия, как перерисовать дугу, так что любая помощь или идея будет принята с благодарностью!

Большое спасибо.

Гранит

+0

Первое предложение: Ваша 'valueLabel' становится нарисованной поверх нее. Старайтесь не воссоздавать его при каждом обновлении, просто измените его текст. Во-вторых, попробуйте повторно использовать подуровень или заменить его. Сделайте 'arc' переменную класса. Затем пройдите через подслои, удалите старую «дугу», а затем переделайте ее с помощью вашего нового случайного поплавка. После того, как 'arc' является переменной класса, вы можете либо заменить его, либо анимировать с нуля, либо вы можете оживить его текущий процент до нового процента. – Putz1103

+0

@ Putz1103 Я сделал arc переменной класса, и я перерисовываю круг, и он работает. Не могли бы вы ответить, чтобы я согласился? :) Спасибо – Granit

ответ

1

Попытка повторного использования подуровень или заменить его. Сделайте дугу переменной класса. Затем перейдите через подслои, удалите старую дугу, а затем переделайте ее с помощью вашего нового случайного поплавка. Когда arc является переменной класса, вы можете либо заменить его, либо анимировать с нуля, либо вы можете оживить его текущий процент до нового процента.

Смежные вопросы