2014-09-21 4 views
22

독일 아이스 하키 리그 DEL에 오늘 위젯을 만들었습니다.iOS 8 오늘 위젯이 잠시 후 작동을 멈 춥니 다

우리 서버에서 다음 게임을로드 중입니다. 테이블보기에 표시합니다. 로드 프로세스는 제안 된 메소드 "widgetPerformUpdateWithCompletionHandler"에서 시작됩니다. 처음에는 "viewWillAppear"에 캐시 된 데이터를로드하고 있습니다.

모든 것이 훌륭합니다!

Screenshot of the working widget.

그러나 위젯 작동이 중지 동안 (한 일) 후

. 알림 센터를 열면 위젯이 정상적으로 나타나지만 다시 업데이트되지 않습니다. 알림 센터에서 위젯을 제거하고 다시 추가해야합니다. 그 후 위젯은 하루 동안 작동 한 다음 다시 작동을 멈 춥니 다.

위젯이 무엇을하는지 보려면 위젯이 아무 것도하지 않는지 확인하기 위해 "widgetPerformUpdateWithCompletionHandler"에 데이터를로드하는 동안 테이블보기 위에 상태 텍스트가있는 간단한 흰색보기를 추가했습니다. 위젯이 작동 중일 때 흰색보기가 나타납니다. 작동하지 않으면 상태보기가 나타나지 않습니다. 그래서 위젯이 잠시 동안 알림 센터에서 활성화 된 후에 메서드 "widgetPerformUpdateWithCompletionHandler"가 호출되지 않는다고 생각합니다.

위젯이 작동을 멈추게하는 원인이 무엇인지 전혀 알지 못합니다. 어떤 아이디어?

답변

19

동일한 문제가있어 응답이 반환되지 않은 경우에도 네트워크 요청 직후에 completionHandler(NCUpdateResultNoData); 을 호출하여 해결했습니다. 완성 처리기가 호출되지 않으면 widgetPerformUpdateWithCompletionHandler 이 더 이상 호출되지 않으므로 더 이상 업데이트가 없을 것입니다. 또한 요청 호출이 반환 된 후에 모든 지점에서 완료 처리기를 호출했는지 확인하십시오.

+0

예, 동일하게 나타났습니다. 나는 몇 가지 시도를하고 네트워크 요청이 약간의 시간 (나쁜 네트워크 조건)이 걸릴 때 widgetPerformUpdateWithCompletionHandler가 다시 호출되지 않는다는 것을 알아 냈다. 완성 처리기가 어떻게 든 무효가된다고 생각합니다. 귀하의 솔루션은 효과가 있지만 의도 된 방식은 아닙니다. 나는 widgetPerformUpdateWithCompletionHandler를 전혀 사용하지 않음으로써 문제를 해결했다. 앞으로도 문제가 해결되기를 바랍니다. –

+0

그래서 widgetPerformUpdateWithCompletionHandler를 사용하지 않는다면 다른 곳에서 네트워크 요청을 실행하고 있습니까? –

+0

예 viewDidAppear에서 네트워크 reuqest를 호출합니다. 따라서 위젯은 백그라운드에서 새로 고침되지 않지만 사용자가 열 때마다 새로 고칩니다. –

13

다른 사람들이 언급했듯이, 이것은 widgetPerformUpdateWithCompletionHandler이 호출 된 후에 이전에 completionHandler을 호출하지 않았기 때문에 발생합니다. completionHandler에 관계없이 호출해야합니다.

나는이 처리 제안하는 방법은 viewDidDisappear 실패로 호출 한 후 인스턴스 변수로 completionHandler을 절약하고하는 것입니다

:

@property(nonatomic, copy) void (^completionHandler)(NCUpdateResult); 
@property(nonatomic) BOOL hasSignaled; 

- (void)widgetPerformUpdateWithCompletionHandler:(void (^)(NCUpdateResult))completionHandler { 
    self.completionHandler = completionHandler; 
    // Do work. 
} 

- (void)viewDidDisappear:(BOOL)animated { 
    [super viewDidDisappear:animated]; 
    if (!self.hasSignaled) [self signalComplete:NCUpdateResultFailed]; 
} 

- (void)signalComplete:(NCUpdateResult)updateResult { 
    NSLog(@"Signaling complete: %lu", updateResult); 
    self.hasSignaled = YES; 
    if (self.completionHandler) self.completionHandler(updateResult); 
} 
+2

나는이 일을 이미하고 있지만, 잠시 후에 위젯이 작동을 멈춘다. – donmarkusi

+0

내가 이것을 시도한 것은 완성 된 블록이 항상 호출되도록하는 합리적인 해결책처럼 보였다. 슬프게도이 방법을 사용한다고해서 문제가 완전히 해결되지는 않습니다. – bencallis

+0

소원 나는 reddit 에서처럼 금을 여기 줄 수 있었다. – maksa

1

를 비동기 호출하기 전에 widgetPerformUpdateWithCompletionHandler 내 NCUpdateResultNewData와 completionHandler를 호출 다시 와서 NCUpdateResultNewData로 다시 호출하거나 NCUpdateResultFailed가 작동하는 것 같습니다.

3

widgetPerformUpdateWithCompletionHandler:이 호출을 중지하고 나면 다른 완료 처리기가 호출되지 않습니다. 시스템 호출을 widgetPerformUpdateWithCompletionHandler:으로 다시 만들 수있는 방법을 찾지 못했습니다. 따라서 위젯이 대체로 viewWillAppear:을 통해 데이터를 다시로드하려고 시도하거나 일부 사용자가로드되지 않는 위젯으로 멈춰있을 수도 있는지 확인하십시오.

+1

슬프게도 이것이 결국 내가했던 일입니다. 위젯 PerformUpdateWithCompletionHandler의 올바른 사용법을 따르려고하는 것이 수치스런 9에서도 작동하지 않는 것은 부끄러운 일입니다.이 제안에 감사드립니다. 실제로이 문제를 해결 한 유일한 것입니다. –

+0

어떻게이 방법에 접근 했습니까? 적절한 완료 처리기가 없다면 시스템은 위젯이 다시 작동하는 것을 결코 알 수 없으므로 viewWillAppear 호출에만 전적으로 의존하게됩니까? 상황이 제대로 작동 할 때 두 번 반복해서 업데이트되지 않도록 동기화를 수행합니까? – RealCasually