块冻结我的应用程序

时间:2014-12-09 14:16:20

标签: ios objective-c iphone objective-c-blocks

我的应用程序存在一个小问题。

当我使用我的块时,应用程序冻结很长时间(差不多1分钟),所以我们什么都不做,所有的滚动/按钮/等都不起作用。

我希望优化我的代码,使其更快地运行,并且用户不必等待1分钟

- (IBAction)exporter:(id)sender {
EKEventStore *store = [[EKEventStore alloc] init];
[store requestAccessToEntityType:EKEntityTypeEvent completion:^(BOOL granted, NSError *error) {
    if (!granted) {
        UIAlertView *alert=[[UIAlertView alloc] initWithTitle:@"Accès aux calendrier" message:@"L'accès au calendrier est nécessaire pour utiliser cette fonctionnalité" delegate:nil cancelButtonTitle:@"OK" otherButtonTitles: nil];
        [alert show];
    }


    EKEvent *event = [EKEvent eventWithEventStore:store];

    Variables *objStatutCompte = [Variables getStatutCompte];

    if([objStatutCompte.statutCompte isEqualToString:@"clt"])
    {
        NSString* titreEvent = [NSString stringWithFormat:@"Intervention avec %@", intervenantRecup];
        event.title=titreEvent;

    }
    else if([objStatutCompte.statutCompte isEqualToString:@"slr"])
    {
        NSString* titreEvent = [NSString stringWithFormat:@"Intervention chez %@", clientRecup];
        event.title=titreEvent;
    }

    NSString* lieuEvent = [NSString stringWithFormat:@"%@, %@", adresseClientRecup, villeRecup];


    event.location=lieuEvent;

    NSString* currentDay = [dateRecup substringWithRange:NSMakeRange(0,2)];
    NSInteger jourCourant = [currentDay integerValue];

    NSString* currentMonth = [dateRecup substringWithRange:NSMakeRange(3,2)];
    NSInteger moisCourant = [currentMonth integerValue];

    NSString* currentYear = [dateRecup substringWithRange:NSMakeRange(6,4)];
    NSInteger anneeCourante = [currentYear integerValue];

    NSString* dateDebut = [NSString stringWithFormat:@"%d-%d-%02d %@:00", anneeCourante, moisCourant, jourCourant, heureDebutRecup];
    NSString* dateFin = [NSString stringWithFormat:@"%d-%d-%02d %@:00", anneeCourante, moisCourant, jourCourant, heureFinRecup];

    NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
    [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
    [dateFormatter setTimeZone:nil];
    NSDate* dateD = [dateFormatter dateFromString:dateDebut];

    NSDate* dateF = [dateFormatter dateFromString:dateFin];

    event.startDate=dateD;
    event.endDate=dateF;

    NSMutableArray *myAlarmsArray = [[NSMutableArray alloc] init];
    EKAlarm *alarm1 = [EKAlarm alarmWithRelativeOffset:-3600]; // 1 Hour
    [myAlarmsArray addObject:alarm1];

    event.alarms=myAlarmsArray;

    [event setCalendar:[store defaultCalendarForNewEvents]];
    NSError *err = nil;
    [store saveEvent:event span:EKSpanThisEvent commit:YES error:&err];

    UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"Evénement ajouté"
                                                    message:@"L'évenement a bien été ajouté"
                                                   delegate:self
                                          cancelButtonTitle:@"Ok"
                                          otherButtonTitles:nil, nil];
    [alert show];

}];

}

2 个答案:

答案 0 :(得分:3)

requestAccessToEntityType的文档说:

  

当用户点击授予或拒绝访问权限时,将在任意队列上调用完成处理程序。当用户决定授予或拒绝权限时,您的应用不会被阻止。

关键是可能不会在主队列上调用completionHandler,但所有UI更新都必须在主线程上进行。

因此,您应该将UI代码分发到主队列:

[store requestAccessToEntityType:EKEntityTypeEvent completion:^(BOOL granted, NSError *error) { 
    dispatch_async(dispatch_get_main_queue(), ^{
        // your code here
    });
}];

答案 1 :(得分:0)

1)用户仪器 - > Time Profiler工具检测app的问题部分: 在Xcode菜单Build-> Profile中,然后选择Time Profiler工具,然后开始记录。像往常一样使用app,然后停止记录。在右下角,您需要检查以下设置: "反转呼叫树","隐藏丢失的符号"。然后找出哪个函数占用了大部分CPU时间

2)根据我的经验,如果您使用某个框架(例如 - SDWebImage),阻止某些线程进行操作,并尝试在此线程中执行某些操作,则可能会发生这种情况。它也可以在主线程中发生......