我正在尝试修改cloudinary的开源库,以便可以收听照片上传的进度。该库类包含一个MultipartUtility
Java类,我对该类进行了修改以侦听上传进度。
修改前的原始代码可以在github上找到:https :
//github.com/cloudinary/cloudinary_java/blob/master/cloudinary-
android/src/main/java/com/cloudinary/android/MultipartUtility.java
我从字面上进行了修改,使其类似于来自另一个支持上传文件/图像等进度的云服务CloudFS的代码:
https://github.com/bitcasa/CloudFS-
Android/blob/master/app/src/main/java/com/bitcasa/cloudfs/api/MultipartUpload.java
package com.cloudinary.android;
import com.cloudinary.Cloudinary;
import java.io.*;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.Map;
/**
* This utility class provides an abstraction layer for sending multipart HTTP
* POST requests to a web server.
*
* @author www.codejava.net
* @author Cloudinary
*/
public class MultipartUtility {
private final String boundary;
private static final String LINE_FEED = "\r\n";
private static final String APPLICATION_OCTET_STREAM = "application/octet-stream";
private HttpURLConnection httpConn;
private String charset;
private OutputStream outputStream;
private PrintWriter writer;
UploadingCallback uploadingCallback;
public final static String USER_AGENT = "CloudinaryAndroid/" + Cloudinary.VERSION;
Long filesize;
public void setUploadingCallback(UploadingCallback uploadingCallback) {
this.uploadingCallback = uploadingCallback;
}
/**
* This constructor initializes a new HTTP POST request with content type is
* set to multipart/form-data
*
* @param requestURL
* @param charset
* @throws IOException
*/
public MultipartUtility(String requestURL, String charset, String boundary, Map<String, String> headers, Long filesize) throws IOException {
this.charset = charset;
this.boundary = boundary;
this.filesize = filesize;
URL url = new URL(requestURL);
httpConn = (HttpURLConnection) url.openConnection();
httpConn.setDoOutput(true); // indicates POST method
httpConn.setDoInput(true);
httpConn.setFixedLengthStreamingMode(filesize); //added this in
if (headers != null) {
for (Map.Entry<String, String> header : headers.entrySet()) {
httpConn.setRequestProperty(header.getKey(), header.getValue());
}
}
httpConn.setRequestProperty("Content-Type", "multipart/form-data; boundary=" + boundary);
httpConn.setRequestProperty("User-Agent", USER_AGENT);
outputStream = httpConn.getOutputStream();
writer = new PrintWriter(new OutputStreamWriter(outputStream, charset), true);
}
public MultipartUtility(String requestURL, String charset, String boundary) throws IOException {
this(requestURL, charset, boundary, null, 0L);
}
/**
* Adds a form field to the request
*
* @param name field name
* @param value field value
*/
public void addFormField(String name, String value) {
writer.append("--" + boundary).append(LINE_FEED);
writer.append("Content-Disposition: form-data; name=\"" + name + "\"").append(LINE_FEED);
writer.append("Content-Type: text/plain; charset=" + charset).append(LINE_FEED);
writer.append(LINE_FEED);
writer.append(value).append(LINE_FEED);
writer.flush();
}
/**
* Adds a upload file section to the request
*
* @param fieldName name attribute in {@code <input type="file" name="..." />}
* @param uploadFile a File to be uploaded
* @throws IOException
*/
public void addFilePart(String fieldName, File uploadFile, String fileName) throws IOException {
if (fileName == null) fileName = uploadFile.getName();
FileInputStream inputStream = new FileInputStream(uploadFile);
addFilePart(fieldName, inputStream, fileName);
}
public void addFilePart(String fieldName, File uploadFile) throws IOException {
addFilePart(fieldName, uploadFile, "file");
}
public void addFilePart(String fieldName, InputStream inputStream, String fileName) throws IOException {
if (fileName == null) fileName = "file";
writer.append("--" + boundary).append(LINE_FEED);
writer.append("Content-Disposition: form-data; name=\"" + fieldName + "\"; filename=\"" + fileName + "\"").append(LINE_FEED);
writer.append("Content-Type: ").append(APPLICATION_OCTET_STREAM).append(LINE_FEED);
writer.append("Content-Transfer-Encoding: binary").append(LINE_FEED);
writer.append(LINE_FEED);
writer.flush();
int progress = 0;
byte[] buffer = new byte[4096];
int bytesRead = -1;
while ((bytesRead = inputStream.read(buffer)) != -1) {
outputStream.write(buffer, 0, bytesRead);
progress += bytesRead;
/* int percentage = ((progress / filesize.intValue()) * 100);*/
if (uploadingCallback != null) {
uploadingCallback.uploadListener(progress);
}
}
outputStream.flush();
writer.flush();
uploadingCallback = null;
inputStream.close();
writer.append(LINE_FEED);
writer.flush();
}
public void addFilePart(String fieldName, InputStream inputStream) throws IOException {
addFilePart(fieldName, inputStream, "file");
}
/**
* Completes the request and receives response from the server.
*
* @return a list of Strings as response in case the server returned status
* OK, otherwise an exception is thrown.
* @throws IOException
*/
public HttpURLConnection execute() throws IOException {
writer.append("--" + boundary + "--").append(LINE_FEED);
writer.close();
return httpConn;
}
}
我所做的更改是按照此线程的建议将以下内容添加到httpURLConnection上:如何在android中实现文件上传进度栏:httpConn.setFixedLengthStreamingMode(filesize);
然后,我创建了一个简单的界面来监听上传进度:
public interface UploadingCallback {
void uploadListener(int progress);
}
然后在HttpURLConnection编写照片时将其附加:
while ((bytesRead = inputStream.read(buffer)) != -1) {
outputStream.write(buffer, 0, bytesRead);
progress += bytesRead;
/* int percentage = ((progress / filesize.intValue()) * 100);*/
if (uploadingCallback != null) {
uploadingCallback.uploadListener(progress);
}
}
代码已运行,但是上传进度似乎无法正确衡量。该照片约为365kb,上传时间大约为十分之一秒(我从17:56:55.481开始上传,并于17:56:55.554开始上传,那仅是0.7秒多一点)。我不认为我的互联网连接速度如此之快,并且期望至少花费5秒钟。我觉得它正在测量将照片写入缓冲区所花费的时间,而不是将其发送到cloudinary服务器所花费的时间。
我怎样才能测量上传照片所需的时间,以便可以将数据用于进度条?
04-24 17:56:55.481 28306-28725/com.a upload 4096
04-24 17:56:55.486 28306-28725/com.a upload 8192
04-24 17:56:55.486 28306-28725/com.a upload 12288
04-24 17:56:55.486 28306-28725/com.a upload 16384
04-24 17:56:55.487 28306-28725/com.a upload 20480
04-24 17:56:55.487 28306-28725/com.a upload 24576
04-24 17:56:55.487 28306-28725/com.a upload 28672
04-24 17:56:55.487 28306-28725/com.a upload 32768
04-24 17:56:55.491 28306-28725/com.a upload 36864
04-24 17:56:55.492 28306-28725/com.a upload 40960
04-24 17:56:55.493 28306-28725/com.a upload 45056
04-24 17:56:55.493 28306-28725/com.a upload 49152
04-24 17:56:55.493 28306-28725/com.a upload 53248
04-24 17:56:55.493 28306-28725/com.a upload 57344
04-24 17:56:55.494 28306-28725/com.a upload 61440
04-24 17:56:55.494 28306-28725/com.a upload 65536
04-24 17:56:55.494 28306-28725/com.a upload 69632
04-24 17:56:55.494 28306-28725/com.a upload 73728
04-24 17:56:55.494 28306-28725/com.a upload 77824
04-24 17:56:55.495 28306-28725/com.a upload 81920
04-24 17:56:55.495 28306-28725/com.a upload 86016
04-24 17:56:55.495 28306-28725/com.a upload 90112
04-24 17:56:55.495 28306-28725/com.a upload 94208
04-24 17:56:55.495 28306-28725/com.a upload 98304
04-24 17:56:55.495 28306-28725/com.a upload 102400
04-24 17:56:55.495 28306-28725/com.a upload 106496
04-24 17:56:55.496 28306-28725/com.a upload 110592
04-24 17:56:55.496 28306-28725/com.a upload 114688
04-24 17:56:55.496 28306-28725/com.a upload 118784
04-24 17:56:55.497 28306-28725/com.a upload 122880
04-24 17:56:55.498 28306-28725/com.a upload 126976
04-24 17:56:55.498 28306-28725/com.a upload 131072
04-24 17:56:55.498 28306-28725/com.a upload 135168
04-24 17:56:55.498 28306-28725/com.a upload 139264
04-24 17:56:55.499 28306-28725/com.a upload 143360
04-24 17:56:55.506 28306-28725/com.a upload 147456
04-24 17:56:55.510 28306-28725/com.a upload 151552
04-24 17:56:55.510 28306-28725/com.a upload 155648
04-24 17:56:55.514 28306-28725/com.a upload 159744
04-24 17:56:55.515 28306-28725/com.a upload 163840
04-24 17:56:55.517 28306-28725/com.a upload 167936
04-24 17:56:55.517 28306-28725/com.a upload 172032
04-24 17:56:55.518 28306-28725/com.a upload 176128
04-24 17:56:55.518 28306-28725/com.a upload 180224
04-24 17:56:55.518 28306-28725/com.a upload 184320
04-24 17:56:55.519 28306-28725/com.a upload 188416
04-24 17:56:55.519 28306-28725/com.a upload 192512
04-24 17:56:55.519 28306-28725/com.a upload 196608
04-24 17:56:55.519 28306-28725/com.a upload 200704
04-24 17:56:55.520 28306-28725/com.a upload 204800
04-24 17:56:55.525 28306-28725/com.a upload 208896
04-24 17:56:55.526 28306-28725/com.a upload 212992
04-24 17:56:55.527 28306-28725/com.a upload 217088
04-24 17:56:55.530 28306-28725/com.a upload 221184
04-24 17:56:55.530 28306-28725/com.a upload 225280
04-24 17:56:55.530 28306-28725/com.a upload 229376
04-24 17:56:55.530 28306-28725/com.a upload 233472
04-24 17:56:55.530 28306-28725/com.a upload 237568
04-24 17:56:55.531 28306-28725/com.a upload 241664
04-24 17:56:55.532 28306-28725/com.a upload 245760
04-24 17:56:55.532 28306-28725/com.a upload 249856
04-24 17:56:55.532 28306-28725/com.a upload 253952
04-24 17:56:55.533 28306-28725/com.a upload 258048
04-24 17:56:55.533 28306-28725/com.a upload 262144
04-24 17:56:55.535 28306-28725/com.a upload 266240
04-24 17:56:55.540 28306-28725/com.a upload 270336
04-24 17:56:55.540 28306-28725/com.a upload 274432
04-24 17:56:55.541 28306-28725/com.a upload 278528
04-24 17:56:55.541 28306-28725/com.a upload 282624
04-24 17:56:55.543 28306-28725/com.a upload 286720
04-24 17:56:55.545 28306-28725/com.a upload 290816
04-24 17:56:55.545 28306-28725/com.a upload 294912
04-24 17:56:55.547 28306-28725/com.a upload 299008
04-24 17:56:55.547 28306-28725/com.a upload 303104
04-24 17:56:55.547 28306-28725/com.a upload 307200
04-24 17:56:55.547 28306-28725/com.a upload 311296
04-24 17:56:55.547 28306-28725/com.a upload 315392
04-24 17:56:55.548 28306-28725/com.a upload 319488
04-24 17:56:55.548 28306-28725/com.a upload 323584
04-24 17:56:55.548 28306-28725/com.a upload 327680
04-24 17:56:55.548 28306-28725/com.a upload 331776
04-24 17:56:55.549 28306-28725/com.a upload 335872
04-24 17:56:55.549 28306-28725/com.a upload 339968
04-24 17:56:55.549 28306-28725/com.a upload 344064
04-24 17:56:55.550 28306-28725/com.a upload 348160
04-24 17:56:55.550 28306-28725/com.a upload 352256
04-24 17:56:55.551 28306-28725/com.a upload 356352
04-24 17:56:55.551 28306-28725/com.a upload 360448
04-24 17:56:55.552 28306-28725/com.a upload 364544
04-24 17:56:55.554 28306-28725/com.a upload 365790
为了自己进行测试,您需要在cloudinary网站上创建一个免费帐户才能获取您的帐户,以便cloudname
可以将Android
SDK连接到他们的服务,以便将未签名的内容直接从android直接上传到他们的服务器。
编辑:
这是我尝试过的方法,当上传实际上在7秒内完成时,它仍在0.7秒内从0-100%跳了起来:
while ((bytesRead = inputStream.read(buffer)) != -1) {
outputStream.write(buffer, 0, bytesRead);
progress += bytesRead;
Log.d("MultiPart", "file transferred so far: "
+ progress);
if (uploadingCallback != null) {
uploadingCallback.uploadListener(progress);
}
Log.d("Flushing", "flush the writer");
outputStream.flush();
writer.flush();
}
使用flush()方法和调用update callback()的时间存在问题。
从代码中可以看到,每次读取图片的一部分时,都将其写入输出缓冲区,但这并不意味着它已发送至服务器,可能已被缓冲,然后稍后写入服务器。 。
您有两个选择,或者在每个outputStream.write()之后调用outputStream.flush(),但这会破坏上载的性能,因为您将失去缓冲的好处。
或者,您可以在方法末尾的outputStream.flush()之后调用updateCallback()。因为在outputStream.flush()之后,您可以确定数据在服务器上,并且进度已经结束。
我正在为Android开发一个包装应用程序,需要连接到相机/照片库(这样用户就可以上传一张自己的照片,例如)。我发现了许多关于这个主题的帖子,包括在WebView中从相机或图库上传图像,以及从WebView输入字段上传相机照片和文件回声器,但我根据这些解决方案建模的代码不起作用。我在openFileChooser函数中放置了一个print语句,当在WebView中单击add Photo/Docum
问题内容: 如何从正在上传图像的AngularJS $ http POST请求中获取“进度”事件?是否可以在客户端进行此操作,还是我需要服务器在接收数据时报告进度? 问题答案: 我认为$ http.post()不能用于此目的。 至于客户端,它应该与HTML5浏览器一起使用,但是您可能必须创建自己的XMLHttpRequest对象和侦听器。
本文向大家介绍Android 拍照并对照片进行裁剪和压缩实例详解,包括了Android 拍照并对照片进行裁剪和压缩实例详解的使用技巧和注意事项,需要的朋友参考一下 Android 拍照并对照片进行裁剪和压缩实例详解 本文主要介绍 Android 调用摄像头拍照并对照片进行裁剪和压缩,文中给出了主要步骤和关键代码。 调用摄像头拍照,对拍摄照片进行裁剪,代码如下。 对拍摄照片进行裁剪,代码如下。 得到
我在Android webview上工作。我在从中的动作上传图像时遇到了问题。在这里,相机打开,我点击图像,但然后什么也没发生,图像无法上传。但它可以很好地与文档或图库。有很多解决方案和这个。但我无法解决我的问题。可以做些什么来解决这个问题? 在我的menifest文件中,我包括: 在我的活动中,我包括: 对于我的WebChromeClient,我包括: 这里可以做些什么,以便图像通过相机动作上传
本文向大家介绍Android拍照得到全尺寸图片并进行压缩,包括了Android拍照得到全尺寸图片并进行压缩的使用技巧和注意事项,需要的朋友参考一下 废话不多说了,直接给大家贴代码了,具体代码如下所示: 以上代码就是本文给大家介绍的Android拍照得到全尺寸图片并进行压缩 的全部内容,希望大家喜欢。
我做错了什么? 这是我的XML文件。课文是德语的,我希望你能理解一切。否则请问我。