首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >具有openParentApplication扩展的Watchkit,WatchKit

具有openParentApplication扩展的Watchkit,WatchKit
EN

Stack Overflow用户
提问于 2015-08-01 16:40:09
回答 2查看 270关注 0票数 0

第一次不起作用“空”(在iPhone中打开应用程序之前)

有些时候不起作用,但我需要一个循环或计时器来重复这个请求,以获得结果:

这是我的密码

代码语言:javascript
复制
- (void)application:(UIApplication *)application handleWatchKitExtensionRequest:(NSDictionary *)userInfo reply:(void (^)(NSDictionary *))reply
{
    // Temporary fix, I hope.
    // --------------------
    __block UIBackgroundTaskIdentifier bogusWorkaroundTask;
    bogusWorkaroundTask = [[UIApplication sharedApplication] beginBackgroundTaskWithExpirationHandler:^{
        [[UIApplication sharedApplication] endBackgroundTask:bogusWorkaroundTask];
    }];
    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
        [[UIApplication sharedApplication] endBackgroundTask:bogusWorkaroundTask];
    });
    // --------------------

    __block UIBackgroundTaskIdentifier realBackgroundTask;
    realBackgroundTask = [[UIApplication sharedApplication] beginBackgroundTaskWithExpirationHandler:^{
        reply(nil);
        [[UIApplication sharedApplication] endBackgroundTask:realBackgroundTask];
    }];

    // Kick off a network request, heavy processing work, etc.

    // Return any data you need to, obviously.
    // reply(nil);
    reply(@{@"Confirmation" : @"Text was received."});

    [[UIApplication sharedApplication] endBackgroundTask:realBackgroundTask];

    //  NSLog(@"User Info: %@", userInfo);




}

监视应用程序代码

代码语言:javascript
复制
- (void)willActivate {
    // This method is called when watch view controller is about to be visible to user
    [super willActivate];




    NSDictionary *dictionary = [[NSDictionary alloc] initWithObjectsAndKeys:@"MyCamande", @"OK", nil];

    [InterfaceController openParentApplication:dictionary reply:^(NSDictionary *replyInfo, NSError *error) {
        NSLog(@"Reply received by Watch app: %@", replyInfo);
    }];

}

怎样才能回忆起最终的结果?

EN

回答 2

Stack Overflow用户

发布于 2015-08-13 16:55:40

嗯,我不建议你使用任何东西,与网络操作有关的手表本身。首先,因为苹果不建议这么做是出于明显的原因。在手表上直接执行的唯一网络操作是加载图像。

我一直在为网络操作而挣扎,并观察了大约一周的时间,并得出结论,目前最稳定的方法是不明显的。

主要问题是WKInterfaceController.openParentApplication(...)不像预期的那样工作。我们不能只要求打开iPhone应用程序并按原样返回响应。有大量的解决方案表明,在- (void)application:(UIApplication *)application handleWatchKitExtensionRequest:(NSDictionary *)userInfo reply:(void (^)(NSDictionary *))reply中创建后台线程会很好,但实际上并非如此。问题是这个方法必须立即发送reply(...);。即使创建同步请求也于事无补,您将继续收到"error -2 iPhone应用程序没有回复“。大概是我们10倍的5倍。

因此,我的解决办法如下:

你实现了:

代码语言:javascript
复制
func requestUserToken() {
        WKInterfaceController.openParentApplication(["request" : "token"], reply: responseParser)
    }

并解析如果没有来自iPhone的响应可能发生的错误响应。

在iOS侧

代码语言:javascript
复制
- (void)application:(UIApplication *)application handleWatchKitExtensionRequest:(NSDictionary *)userInfo reply:(void (^)(NSDictionary *))reply
{


    __block UIBackgroundTaskIdentifier watchKitHandler;
    watchKitHandler = [[UIApplication sharedApplication] beginBackgroundTaskWithName:@"backgroundTask"
                                                                   expirationHandler:^{
                                                                       watchKitHandler = UIBackgroundTaskInvalid;
                                                                   }];

    NSString *request = userInfo[@"request"];

    if ([request isEqualToString:@"token"])
    {
        reply(@{@"token" : @"OK"});

        [PSWatchNetworkOperations.shared loginUser];
    } 

    dispatch_after( dispatch_time( DISPATCH_TIME_NOW, (int64_t)NSEC_PER_SEC * 1 ), dispatch_get_global_queue( DISPATCH_QUEUE_PRIORITY_DEFAULT, 0 ), ^{
        [[UIApplication sharedApplication] endBackgroundTask:watchKitHandler];
    } );
}

这段代码只是创建一个后台线程,强制iPhone发送网络请求。让我们想象一下,您的iPhone应用程序中有一个特殊的类,它将发送这些请求并发送答案以供观看。就目前而言,这只能使用App组完成。因此,您必须为应用程序和watchkit扩展创建一个应用程序组。之后,我建议使用MMWormhole来建立应用程序和扩展程序之间的通信。这本手册很能自我解释。

现在这一切的意义是什么。您必须实现发送请求到服务器和发送响应通过虫洞。我使用ReactiveCocoa,所以代码中的示例如下所示:

代码语言:javascript
复制
- (void)fetchShoppingLists
{
    RACSignal *signal = [PSHTTPClient.sharedAPIClient rac_GET:@"list/my" parameters:@{@"limit":@20, @"offset":@0} resultClass:PSShoppingListsModel.class];
    [signal subscribeNext:^(PSShoppingListsModel* shoppingLists) {
        [self.wormHole passMessageObject:shoppingLists identifier:@"shoppingLists"];
    }];

    [signal subscribeError:^(NSError *error) {
        [self.wormHole passMessageObject:error identifier:@"error"];
    }];
}

正如您在这里看到的,我将返回响应对象或错误。请注意,您通过虫洞发送的所有内容都应该与NSCoding兼容。

现在,您可能会像这样解析响应:

代码语言:javascript
复制
override func awakeWithContext(context: AnyObject?) {
    super.awakeWithContext(context)

    PSWatchOperations.sharedInstance.requestUserToken()

    PSWatchOperations.sharedInstance.wormhole.listenForMessageWithIdentifier("token", listener: { (messageObject) -> Void in
        // parse message object here
        }
    })

}

所以,给出一个结论。向父应用程序发送请求,以便从后台唤醒并启动异步操作。立即回复()。当您收到来自操作的答复时,发送您已经得到响应的通知。同时,听听你的watchExtension中的回应。

对不起,那是很多短信,但我只希望它能帮你保持冷静,因为我在这方面花了很多时间。

票数 1
EN

Stack Overflow用户

发布于 2015-08-03 21:16:08

也许你可以试着更清楚地解释这个问题。但是,您可能想要做的一件事是在awakeWithContext中调用awakeWithContext:而不是willActivate。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/31763859

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档