子视图的 viewDidAppear

Posted

技术标签:

【中文标题】子视图的 viewDidAppear【英文标题】:viewDidAppear for subviews 【发布时间】:2011-03-29 09:38:41 【问题描述】:

我想在按下按钮时加载一些数据,并在加载时将“加载视图”显示为当前视图的子视图。

所以我只想在子视图出现后才开始加载。如果不是,我的 UI 在没有通知的情况下卡住(并且子视图仅在加载完成后显示)。

有没有办法使用viewDidAppearfor subviews 之类的东西?

像这样在addSubview: 之后立即工作是行不通的:

- (void)doSomeWorkAndShowLoadingView

    UIView *loadingView = [[[UIView alloc] initWithFrame:self.view.frame] autorelease];
    loadingView.backgroundColor = [UIColor redColor];
    [self.view addSubview:loadingView];
    [self doSomeWork];
    [loadingView removeFromSuperview];

- (void)doSomeWork
 
    sleep(5);

(我不想在新线程上加载,因为我正在处理的是 CoreData,它不是线程安全的)。

谢谢!

【问题讨论】:

【参考方案1】:

我找到了解决办法:

添加带有动画的子视图,我可以使用- (void)animationDidStop:(CAAnimation *)anim finished:(BOOL)flag 调用子视图代表的subviewDidAppear 之类的东西。

在 UIView 的子类中:

#define KEY_SHOW_VIEW @"_ShowLoadingView_"
#define KEY_HIDE_VIEW @"_HideLoadingView_"
- (void)addToSuperview:(UIView *)theSuperview


    [theSuperview addSubview:self];   

    CATransition *animation = [CATransition animation];
    [animation setDuration:0.2];
    [animation setType:kCATransitionFade];
    [animation setDelegate:self];
    [animation setRemovedOnCompletion:NO];
    [animation setValue:KEY_SHOW_VIEW forKey:@"animation_key"];
    [[theSuperview layer] addAnimation:animation forKey:nil];



- (void)removeFromSuperview

    CATransition *animation = [CATransition animation];
    [animation setDuration:0.2];
    [animation setType:kCATransitionFade];
    [animation setDelegate:self];
    [animation setRemovedOnCompletion:NO];
    [animation setValue:KEY_HIDE_VIEW forKey:@"animation_key"];
    [[self.superview layer] addAnimation:animation forKey:nil]; 

    [super removeFromSuperview];


- (void)animationDidStop:(CAAnimation *)anim finished:(BOOL)flag
    
    NSString* key = [anim valueForKey:@"animation_key"];
    if ([key isEqualToString:KEY_SHOW_VIEW]) 
        if (self.delegate) 
            if ([self.delegate respondsToSelector:@selector(loadingViewDidAppear:)]) 
                [self.delegate loadingViewDidAppear:self];
             
        
     else if ([key isEqualToString:KEY_HIDE_VIEW])
        [self removeFromSuperview];
    

这让我得到了我正在寻找的结果。

再次感谢您的帮助!

【讨论】:

【参考方案2】:

您应该能够在调用 [parentView addSubview:loadingView] 后直接开始加载,或者在加载视图中(假设它是子类)覆盖 didMoveToSuperview,如下所示:

- (void)didMoveToSuperview 
    // [self superview] has changed, start loading now...

【讨论】:

不起作用。 didMoveToSuperview 并不意味着子视图确实出现了,而只是它已被添加到超级视图中。如果我开始在didMoveToSuperview 中加载,子视图仍然只有在加载数据后才可见。 当你说“加载”时,你在做什么?您是在等待网络操作还是在执行某种计算? 我从 CoreData 数据库加载数据。 其实不是“加载”。我将数据从一个对象复制到另一个对象。 这听起来绝对像是应该在主线程之外完成的事情。如果这不是一个选项,您可能想在添加加载子视图后立即尝试调用您的 doSomeWork 方法。像这样:[self performSelector:@selector(doSomeWork) withObject:nil afterDelay:1/10]

以上是关于子视图的 viewDidAppear的主要内容,如果未能解决你的问题,请参考以下文章

如何删除子视图(或视图的所有子视图)

将子视图添加到 self.view 但让某些子视图内容不被添加的子视图覆盖

如何在禁用父视图(不是子视图)的父视图上打开子视图(自定义)?

试图向视图添加子视图,但子视图不显示

问题:当子视图移出超级视图时,子视图位于超级视图之上

iOS - 将子视图添加到子视图控制器视图