我需要从View(android.webkit.WebView)捕获一个Image并将其保存为Android设备上的PNG文件。
我应该使用AsyncTasks保存图像以避免阻止UI线程吗?
我应该从AsyncTask doInBackground方法中删除哪些代码?
代码:
private void getWebScreenshot() {
String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date());
String imageFileName = "IMG_" + timeStamp;
File storageDir = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DCIM);
String filePath = storageDir + "/" + imageFileName + ".png";
String state = Environment.getExternalStorageState();
if (Environment.MEDIA_MOUNTED.equals(state)) {
// Log.i(LOGTAG, "External Storage Available");
// Create the storage directory if it does not exist
if (!storageDir.exists()) {
// Log.i(LOGTAG,"storageDir does not exists");
if (!storageDir.mkdirs()) {
// Log.d(LOGTAG, "Failed to create the directory");
}
}
// Create bitmap screen capture
Bitmap bitmap;
View sview = findViewById(R.id.web_view);
sview.setDrawingCacheEnabled(true);
bitmap = Bitmap.createBitmap(sview.getDrawingCache());
sview.setDrawingCacheEnabled(false);
FileOutputStream fout = null;
File imageFile = new File(filePath);
try {
fout = new FileOutputStream(imageFile);
bitmap.compress(Bitmap.CompressFormat.PNG, 100, fout);
fout.flush();
fout.close();
// Tell the media scanner about the new file so that it is
// immediately available to the user.
MediaScannerConnection.scanFile(this,
new String[]{imageFile.toString()}, null,
new MediaScannerConnection.OnScanCompletedListener() {
public void onScanCompleted(String path, Uri uri) {
// Log.i(LOGTAG, "ExternalStorage Scanned " + path + ":");
// Log.i(LOGTAG, "ExternalStorage > uri: " + uri);
}
});
// Log.i(LOGTAG, "Success");
} catch (IOException e) {
e.printStackTrace();
}
}
}
答案 0 :(得分:1)
是的,绝对必须在后台线程中执行此操作。所有I / O操作都必须在后台线程上完成,因为无法保证操作完成的速度有多快 - 可能需要几毫秒到几分钟(这是一个非常糟糕的糟糕情况)。所有对存储,数据库,Web资源等的访问都必须在后台线程上完成。
使用多个线程可能会导致同步问题。仅移动到执行I / O操作的代码的单独线程。
希望这会有所帮助:)
答案 1 :(得分:1)
答案是肯定的,您不想阻止您的UI线程。 更好的解决方案是将图像保存在其他线程中,同时通知用户,这样他就会知道图像正在保存(启用按钮,加载器gif ......)。
线程中的所有内容都可以接受您采用时间戳的部分,因为您可能会意外地创建两个具有相同名称的文件