2011-03-05 6 views
1

다음 코드가 있습니다.메서드 호출 순서가 잘못 되었습니까?

 [self.view bringSubviewToFront:loggingIn]; 
    [self loginWithUsername:user Password:pw]; 

이것은 단추 누름에 대한 IBAction 메서드 안에 있습니다. 사용자가 로그인 할 때까지 버튼이 강조 표시된 채로 있습니다 (몇 초 정도 걸릴 수 있음). 그러면보기가 나타납니다. 로그인 메소드가 호출되기 전에 어떻게 뷰가 나타나지 않습니까?

+0

실마리를 얻을 수 있다면 더 많은 코드를 게시해야한다고 생각합니다. 문제는 아마 login-method가 메인 스레드를 잡고 있다는 것입니다. – Jensen2k

답변

2

존의 대답은 효과가 있지만 스레드를 실행하는 것보다 실행 루프와 관련이 있습니다. 기본적으로 앱이 버튼을 클릭하는 것과 같은 이벤트를 받으면 핸들러가 주 스레드에서 실행됩니다. UI 변경 사항은 핸들러가 완료된 후에 발생합니다. 이를 통해 코코아는이를 분석/수행함으로써 그래픽 업데이트를 최적화 할 수 있습니다. 비밀번호 : : [원문] 방법 당신의 loginWithUsername를 호출하기 전에 -

Run Loop: 
    Event -> Your Handler Code -> System Updates UI 

그래서 당신은 시스템이 UI 업데이트를 시작하도록하기 위해 핸들러 코드를 완료하도록 할 필요가있다. 타이머를 예약하면 실행 루프의 다음 반복으로 넘어갑니다 (타이머가 꺼지면 다음 루프를 트리거하는 "이벤트"가됩니다). 그래서,

Run Loop (2 iterations): 
    Mouse Click -> Your Handler Code (reorder views) -> System reorders views 
    Timer Fires -> Your Handler Code (trigger login) -> Any addl UI updates 

그래서 같은 것을 할 :

- (void) buttonHandler: (id)sender { 
    [self.view bringSubviewToFront:loggingIn]; 
    [self performSelector: @selector(performLogin) 
       withObject: [NSArray arrayWithObjects:user, pw, nil] 
       afterDelay: 0]; 
} 

- (void) performLogin: (NSArray *)args { 
    [self loginWithUsername:[args objectAtIndex:0] Password:[args objectAtIndex:1]]; 
} 

이 배열 될 필요가 없습니다. 사전에 사용자 이름과 암호를 압축하여 대신 인수로 사용할 수도 있습니다.

+0

설명 주셔서 감사합니다! 그게 효과가있어. – Paludis

1

첫 번째 호출은 두 번째 줄에 의해 차단 된 다른 스레드에서 실행됩니다. 두 번째 전화를 0.1 초 정도 지연 시키려면 다음을 사용하십시오.

- (void)performSelector:(SEL)aSelector withObject:(id)anArgument afterDelay:(NSTimeInterval)delay 

NSObject 방법. 두 개의 인자를 사용하고 있기 때문에 둘을 하나의 객체로 전달하거나 인스턴스 변수를 사용해야합니다.

관련 문제