2011-08-26 42 views
3

我有一个phonegap应用程序,我想在Documents文件夹中运行一个非常简单的“does file exists”命令。我主要工作。在JS,我有:从目标c返回变量为javascript

fileDownloadMgr.fileexists("logo.png"); 
...... 
PixFileDownload.prototype.fileexists = function(filename) { 
    PhoneGap.exec("PixFileDownload.fileExists", filename); 
}; 

然后在Objective C,我有:

-(BOOL) fileExists:(NSMutableArray*)paramArray withDict:(NSMutableDictionary*)options;{ 
    NSString * fileName = [paramArray objectAtIndex:0]; 

    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES); 
    NSString *documentsDirectory = [paths objectAtIndex:0]; 
    NSString *newFilePath = [documentsDirectory stringByAppendingString:[NSString stringWithFormat: @"/%@", fileName]]; 

    BOOL isMyFileThere = [[NSFileManager defaultManager] fileExistsAtPath:newFilePath]; 

    //i'm stuck here 
} 

我可以使用的NSLog打印此控制台看到,逻辑不工作和BOOL设置正确。但我需要在JavaScript世界中的变量。我知道stringByEvaluatingJavaScriptFromString,但这只会执行JavaScript,即调用回调函数。这不是我所需要的在这里,我需要(在JavaScript):

var bool = fileDownloadMgr.fileexists("logo.png"); 
if(bool) alert('The file is there!!!!!!'); 

什么我需要做回从目标C回的JavaScript布尔?

回答

6

由于PhoneGap.exec的调用是异步的,因此您需要传递一个在被调用的Objective-C方法成功时调用的函数。让成功处理函数的参数来fileexists(为什么稍后解释的原因):

PixFileDownload.prototype.fileexists = function(filename, success) { 
    PhoneGap.exec(success, null, "PixFileDownload", "fileExists", filename); 
}; 

的第二个参数是PhoneGap.exec一个错误处理程序,闲置在这里。

在Obj-C方法中,使用PluginResult通过-resultWithStatus:messageAsInt:方法将结果传递给成功函数。

-(BOOL) fileExists:(NSMutableArray*)paramArray withDict:(NSMutableDictionary*)options;{ 
    ... 
    //i'm stuck here 
    /* Create the result */ 
    PluginResult* pluginResult = [PluginResult resultWithStatus:PGCommandStatus_OK 
               messageAsInt:isMyFileThere]; 
    /* Create JS to call the success function with the result */ 
    NSString *successScript = [pluginResult toSuccessCallbackString:self.callbackID]; 
    /* Output the script */ 
    [self writeJavascript:successScript]; 

    /* The last two lines can be combined; they were separated to illustrate each 
    * step. 
    */ 
    //[self writeJavascript: [pluginResult toSuccessCallbackString:self.callbackID]]; 
} 

如果OBJ - C的方法可能会导致错误的条件下,使用PluginResulttoErrorCallbackString:创建一个调用的误差函数的脚本。确保你还传递一个错误处理程序作为PhoneGap.exec的第二个参数。

协调&延续现在

,用于将success参数fileexists承诺的解释。 “协调”是计算的一个特征,意味着代码在其依赖的任何计算完成之前不会运行。同步调用免费提供协调,因为函数在计算完成之前不会返回。使用异步调用时,您需要注意协调。你可以通过在称为“continuation”的函数中捆绑相关代码来实现这一点(这意味着“从给定点向前的其余计算”)并将此延续传递给异步函数。这被称为(不出所料)continuation passing style(CPS)。请注意,您可以在同步调用中使用CPS,但它不太常见。

PhoneGap.exec是异步的,所以它接受continuation,一个调用成功,一个失败。 fileexists依赖于异步函数,因此它本身是异步的,需要传递一个延续。 fileDownloadMgr.fileexists("logo.png");之后的代码应该包含在传递给fileexists的函数中。例如,如果你本来有:

if (fileDownloadMgr.fileexists("logo.png")) { 
    ... 
} else { 
    ... 
} 

创建一个延续,是简单的,但它可以得到一点毛茸茸的,当你有多个延续。重写if语句作为功能,具有可变取代调用异步函数:

function (x) { 
    if (x) { 
     ... 
    } else { 
     ... 
    } 
} 

这个延续然后传递给fileexists

fileDownloadMgr.fileexists("logo.png", function (exists) { 
    if (exists) { 
     ... 
    } else { 
     ... 
    } 
}); 

进一步阅读

我做不到找到PluginResult-resultWithStatus:messageAsInt:,但是有一个例子展示了如何从Obj-C方法返回一个值到“How to Create a PhoneGap Plugin for iOS”中的JS。 API文档中PhoneGap.exec的文档目前相当差。既然都是维基页面,或许我或其他人会找到改进它们的时间。 PluginResult也有headerimplementation文件。

+0

outis我跟着你继续执行。你能提供一个更清晰的例子吗?谢谢 – user7865437