var camera = {
settings : {
quality : 50,
targetWidth : 1024,
targetHeight : 1024,
correctOrientation : true
}
};
var error = function(message) {
alert("Error happened while trying to get a picture", message);
};
document.addEventListener("deviceready", function() {
camera.toFile = function() {
this.settings.destinationType = navigator.camera.DestinationType.FILE_URI;
return this;
},
camera.toBase64 = function() {
this.settings.destinationType = navigator.camera.DestinationType.DATA_URL;
return this;
},
camera.fromCamera = function() {
this.settings.sourceType = navigator.camera.PictureSourceType.CAMERA;
return this;
};
camera.fromLibrary = function() {
this.settings.sourceType = navigator.camera.PictureSourceType.PHOTOLIBRARY;
return this;
};
camera.fromPhotoAlbum = function() {
this.settings.sourceType = navigator.camera.PictureSourceType.SAVEDPHOTOALBUM;
return this;
}
camera.get = function(callback) {
navigator.camera.getPicture(function(data) {
alert("taking a picture successful");
callback(data);
}, error, camera.settings);
};
}, false);
这是我的相机的小包装。我称之为:
camera.fromPhotoAlbum().toBase64().get(function(base64){});
大约20%的时间,“警报(”拍照成功“);”没有被调用,而没有显示错误。如果我取消拍照,会显示一条警告,显示“尝试拍照时发生错误”消息,因此错误回调有效。
基本上没有任何反应。我已经在CM9上的三星Galaxy S2和全新的HTC One X上进行了测试。
答案 0 :(得分:11)
最近我回答了another question同样的问题。我们在我的公司碰到了这个并解决了它。它与Android系统有关,而不是Phonegap。
当您启动相机时,您的应用进入onStop()会发生什么。在那里,如果需要内存,Android系统有权杀死你的应用程序。事实上,当相机拍照并将其转储到内存中时,内存通常会变低,因此您的应用很可能会在用户拍照时被杀死。
现在你的应用程序已经死了,当相机完成时,它会重启你的应用程序。这就是为什么它表现得如此奇怪;相机回到你的应用程序,但不是之前的相同实例,所以你的回调永远不会被调用,因为它不再存在。
您可以通过降低图片质量并通过URI而不是数据将其传递到您的应用来降低发生这种情况的频率,但问题不会完全消失。
为了解决从未发生过的回调问题,我们制作了一个Java回调函数,启动摄像头并在每次拍摄时将图片保存到同一位置。然后,当应用程序从被杀死开始时,它会在该位置查找该图片。
对于一个愚蠢的问题,这是一个奇怪的解决方案,但如果您的应用程序被杀死,那么相机回调就不会发生。如果您需要有关如何使Java回调执行此操作的更多信息,请告诉我,我会将代码放在此处。否则,请查看this SO answer以获取更多信息。
编辑:这是我们在主要DroidGap活动中使用的代码:
private static final String folderPath = Environment.getExternalStorageDirectory().getAbsolutePath() + "/appName";
private static final String filePath = "phonegapImage.jpg";
@Override
public void onCreate(Bundle savedState) {
//...The rest of onCreate, this makes the Java available in JavaScript
appView.addJavascriptInterface(this, "Camera");
}
public void takePhoto(final String callback) {
Log.v("Camera Plugin", "Starting takePhoto callback");
Intent intent = new Intent(android.provider.MediaStore.ACTION_IMAGE_CAPTURE);
intent.putExtra(android.provider.MediaStore.EXTRA_OUTPUT, Uri.fromFile(new File(folderPath, filePath)));
startActivityForResult(intent, TAKE_PICTURE);
}
public String getPhotoUri() {
return Uri.fromFile(new File(folderPath, filePath)).toString();
}
@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
switch (requestCode) {
case TAKE_PICTURE:
if (resultCode == Activity.RESULT_OK) {
//Do whatever you need to do when the camera returns
//This is after the picture is already saved, we return to the page
}
break;
default:
Log.v("Camera", "Something strange happened...");
break;
}
}
然后,在您的JavaScript中,您可以使用以下方法调用相机:
Camera.takePhoto("onPhotoURISuccess");
//Then, to get the location of the photo after you take it and load the page again
var imgPath = Camera.getPhotoUri();
所以,就是这样。只需确保将所有路径/文件/页面/等名称更改为您要在应用中使用的名称。这将在每次拍摄照片时覆盖该图像,但如果您不想这样,您可能会想出一些动态命名它们。您可以像使用JavaScript中的任何其他路径一样使用该URI。