Question

I want to use a little animation for my labels. If I try to call this animation from a IBAction button or ViewDidLoad and all work correctly.

- (void)animateLabelShowText:(NSString*)newText characterDelay:(NSTimeInterval)delay
{    
    [self.myLabel setText:@""];

    for (int i=0; i<newText.length; i++)
    {
        dispatch_async(dispatch_get_main_queue(),
        ^{
            [self.myLabel setText:[NSString stringWithFormat:@"%@%C", self.myLabel.text, [newText characterAtIndex:i]]];
        });

        [NSThread sleepForTimeInterval:delay];
    }
}

called by:

-(void) doStuff
{
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_LOW, 0),
    ^{
        [self animateLabelShowText:@"Hello Vignesh Kumar!" characterDelay:0.5];
    });
}

But if I put this method in a protocol and I try to call it from for example a delegate nothing appears. There's probably I missing something in the GDC (Grand Central Dispatch) logics:

...
 if ([_myDelegate respondsToSelector:@selector(doStuff:)])
 {
     NSLog(@" Yes I'm in and try to execute doStuff..");
     [_myDelegate doStuff]; // NOTHING TO DO
 }
...

The same situation happened when I change my function doStuff with any similar function like:

-(void)typingLabel:(NSTimer*)theTimer
{
    NSString *theString = [theTimer.userInfo objectForKey:@"string"];
    int currentCount = [[theTimer.userInfo objectForKey:@"currentCount"] intValue];
    currentCount ++;
    NSLog(@"%@", [theString substringToIndex:currentCount]);

    [theTimer.userInfo setObject:[NSNumber numberWithInt:currentCount] forKey:@"currentCount"];

     if (currentCount > theString.length-1) {
        [theTimer invalidate];
    }

    [self.myLabel setText:[theString substringToIndex:currentCount]];
}

called by

-(void) doStuff
{
    NSString *string =@"Risa Kasumi & Yuma Asami";

    NSMutableDictionary *dict = [NSMutableDictionary dictionary];
    [dict setObject:string forKey:@"string"];
    [dict setObject:@0 forKey:@"currentCount"];
    NSTimer *timer = [NSTimer scheduledTimerWithTimeInterval:0.1 target:self selector:@selector(typingLabel:) userInfo:dict repeats:YES];
    [timer fire];
}
Was it helpful?

Solution

I've solved using NSNotificationCenter in my delegate file .m

in viewDidLoad:

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(makeEffectOnMyLabel:) name:@"lblUpdate" object:nil];

in my protocol function :

dispatch_async( dispatch_get_main_queue(),
    ^{
        ...I've populated a dictionary userInfo with my vars
        [[NSNotificationCenter defaultCenter] postNotificationName:@"lblUpdate" object:nil userInfo:userInfo];
    });

in a function created to prepare typingLabel

-(void) makeEffectOnMyLabel:(NSNotification *) notification
{
    ..changes between dictionaries to prepare typingLabel..

    NSMutableDictionary *dict = [NSMutableDictionary dictionary];
    NSDictionary* userInfo = [notification userInfo];

    [dict setObject:[userInfo objectForKey:@"myRes"] forKey:@"myRes"];
    [dict setObject:[userInfo objectForKey:@"myType"] forKey:@"myType"];
    [dict setObject:[userInfo objectForKey:@"frase"] forKey:@"frase"];
    [dict setObject:@0 forKey:@"currentCount"];
    NSTimer *timer = [NSTimer scheduledTimerWithTimeInterval:0.1 target:self selector:@selector(typingLabel:) userInfo:dict repeats:YES];
    [timer fire];
}

Now all work correct.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top