从 iOS cordova 中的委托方法发送 pluginResult
Posted
技术标签:
【中文标题】从 iOS cordova 中的委托方法发送 pluginResult【英文标题】:Sending pluginResult from delegate method in iOS cordova 【发布时间】:2014-01-24 00:30:19 【问题描述】:我有一个问题似乎尚未得到解答。我是cordova的新手,所以我不确定这是否是框架中的调用。我有一个使用 Zbar libaray 扫描条形码的插件。扫描结果由委托管理,并在 imagePickerController:didFinishPickingMediaWithInfo: 方法中返回。我的插件调用了 scan 方法,但在我的 scan 方法结束后返回。我需要它将日期返回到我请求它的网站。我需要知道如何让我的扫描方法等待我的 zbar 委托完成,然后再发送对我的 webview 的响应。如果您能为我解决这个问题,请提前感谢您。并且没有调用 [super writejavascript:jsCallback] 不起作用,我使用的是cordova而不是phonegap。
#import "Camera.h"
#import <Cordova/CDV.h>
#import "AppDelegate.h"
@implementation Camera
@synthesize resultStr, command, hasPendingOperation;
//Override
- (void)pluginInitialize
NSLog(@"%@", @"init Camera");
- (void)scan:(CDVInvokedUrlCommand*)mycommand
NSLog(@"%@", @"Camera.scan");
self.command = mycommand;
ZBarReaderViewController *reader = [ZBarReaderViewController new];
reader.readerDelegate = self;
reader.supportedOrientationsMask = ZBarOrientationMaskAll;
ZBarImageScanner *scanner = reader.scanner;
// TODO: (optional) additional reader configuration here
// EXAMPLE: disable rarely used I2/5 to improve performance
[scanner setSymbology: ZBAR_I25
config: ZBAR_CFG_ENABLE
to: 0];
// present and release the controller
[self.viewController presentViewController:reader animated:YES completion:nil];
NSLog(@"%@", @"finsihed plugin");
- (void) imagePickerController: (UIImagePickerController*) reader
didFinishPickingMediaWithInfo: (NSDictionary*) info
// ADD: get the decode results
id<NSFastEnumeration> results =
[info objectForKey: ZBarReaderControllerResults];
ZBarSymbol *symbol = nil;
for(symbol in results)
// EXAMPLE: just grab the first barcode
break;
self.resultStr = symbol.data;
// ADD: dismiss the controller (NB dismiss from the *reader*!)
[reader dismissViewControllerAnimated:YES completion:nil];
CDVPluginResult* pluginResult = nil;
if (self.resultStr != nil && [self.resultStr length] > 0)
pluginResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:self.resultStr];
else
pluginResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_ERROR messageAsString:@"Failed to scan barcode!"];
NSLog(@"%@", self.resultStr); //<----- this is the date I need to return to my //webview this issue is scan: has already completed and returned
[self.commandDelegate sendPluginResult:pluginResult callbackId:command.callbackId];
@end
【问题讨论】:
【参考方案1】:当您从 javascript 调用插件时,您会提供成功和失败的回调。此回调是插件将值传回 Web 层的唯一方式。
具体来说,你的 javascript 看起来像这样。
cordova.exec(
function (result)
// do stuff with plugin result! Hurray!
,
function (error)
self.alert("Things went downhill, sorry... :\r\r" + error);
,
"PluginName", "MethodName", [parameters]
);
由于插件结果已经通过回调传递,因此它是由委托提供的这一事实应该是无关紧要的。
更新
您的问题询问有关在 Objective-C 端等待的问题。 不要等待。这不是 Cordova 的设计方式,如果您没有立即从调用中返回,您甚至会看到控制台中弹出警告。
Cordova 插件调用旨在调用异步回调,您必须围绕这些回调设计 Web 界面。
一种常见的方法是在执行调用时显示微调器或占位符文本
-
显示微调器或占位符文本(“检索数据”)
调用插件
在回调中:
-
移除微调器/占位符。
显示结果。
【讨论】:
我同意这一点,因此这就是我的 JS 方面的工作方式。然而问题是被调用的“MethodName”,在这种情况下是 scan: 将在方法运行后返回。因此,当显示扫描仪视图时,插件已经返回到我的 JS 端。我需要找到一种方法让它等待我的代表返回日期。【参考方案2】:我发现了这个问题,它与UIImagePickerController
的范围有关。当委托方法运行时,这个对象是唯一仍在范围内的东西。我错误地将回调 ID 保存为类属性,我以为在调用 imagePickerController:didFinishPickingMediaWithInfo:
方法时可以检索它。
解决方法只是扩展 ZBAR 阅读器类并添加一个属性,以便我可以存储回调 ID。所有 Cordova 插件都需要正确的回调 ID 才能返回 JS 端属性。
【讨论】:
你是如何调用目标 C 方法扫描的:来自 javascript?我在使用自定义插件时遇到问题以上是关于从 iOS cordova 中的委托方法发送 pluginResult的主要内容,如果未能解决你的问题,请参考以下文章
使用委托从iOS中的ViewModel传递数据到UI的任何替代方法?