java - 将 Base64 格式的大图片上传到服务器

标签 java android image

我使用 android.hardware.Camera 拍照API。然后,我将其转换为实际大小一半的位图,将其压缩为质量 8​​0 的 JPEG,将其转换为 Base64 并将其发送到服务器,如下所示。

ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
bitmap.compress(Bitmap.CompressFormat.JPEG, 80, byteArrayOutputStream);
byte[] byteArray = byteArrayOutputStream.toByteArray();
String encoded = Base64.encodeToString(byteArray, Base64.NO_WRAP);
String json_response = "";

try {
    URL url = new URL("https://example.com/api_endpoint");
    HttpURLConnection conn = (HttpURLConnection) url.openConnection();
    conn.setReadTimeout(15000);
    conn.setConnectTimeout(15000);
    conn.setRequestMethod("POST");
    conn.setDoInput(true);
    conn.setDoOutput(true);
    OutputStream os = conn.getOutputStream();
    BufferedWriter writer = new BufferedWriter(
            new OutputStreamWriter(os, "UTF-8"));
    writer.write("?reg=" + regCode);
    writer.write("&img=" + encoded);
    writer.flush();
    writer.close();
    os.close();
    Log.d("Auth", conn.getResponseCode() + "");
    InputStreamReader in = new InputStreamReader(conn.getInputStream());
    BufferedReader br = new BufferedReader(in);
    String text = "";
    while ((text = br.readLine()) != null) {
        json_response += text;
    }
    conn.disconnect();
} catch (IOException e) {
    Log.d(getClass().getName(), "" + e.getMessage());
}  

这按预期工作。现在,如果我不调整图像大小并保持 100% 质量,我应该如何避免 OutOfMemoryError?我的应用程序要求图像具有全分辨率和最佳质量。

我的问题是:

  1. 我的上传方式正确吗?
  2. 如何以最佳质量发送图像而不发生OutOfMemoryError,即如何在此过程中优化 RAM 使用?

最佳答案

这是我的图像/文件 uploader 类:

public class ImageUploader extends AsyncTask<String, String, String> {

    File imageFile = null;
    String fileName = null;

    public ImageUploader(File imageFile, String fileName){
        this.imageFile = imageFile;
        this.fileName = fileName;
    }

    @Override
    protected String doInBackground(String... params) {
        String url_str = params[0];

        String lineEnd = "\r\n";
        String twoHyphens = "--";
        String boundary = "*****";
        String Tag="fSnd";

        try {
            URL url = new URL(url_str);
            HttpURLConnection c = (HttpURLConnection) url.openConnection();

            c.setRequestMethod("POST");

            c.setDoInput(true);
            c.setDoOutput(true);

            c.setRequestProperty("Connection", "Keep-Alive");
            c.setRequestProperty("Content-Type", "multipart/form-data;boundary=" + boundary);

            c.connect();

            DataOutputStream dos = new DataOutputStream(c.getOutputStream());

            dos.writeBytes(twoHyphens + boundary + lineEnd);
            dos.writeBytes("Content-Disposition: form-data; name=\"file\";filename=\"" + this.fileName + "\"" + lineEnd);
            dos.writeBytes(lineEnd);

            FileInputStream fin = new FileInputStream(imageFile);

            int bytesAvailable = fin.available();

            int maxBufferSize = 1024;
            int bufferSize = Math.min(bytesAvailable, maxBufferSize);
            byte[ ] buffer = new byte[bufferSize];

            int bytesRead = fin.read(buffer, 0, bufferSize);

            while (bytesRead > 0)
            {
                dos.write(buffer, 0, bufferSize);
                bytesAvailable = fin.available();
                bufferSize = Math.min(bytesAvailable,maxBufferSize);
                bytesRead = fin.read(buffer, 0,bufferSize);
            }


            dos.writeBytes(lineEnd);
            dos.writeBytes(twoHyphens + boundary + twoHyphens + lineEnd);

            fin.close();
            dos.flush();
            dos.close();

            StringBuilder response = new StringBuilder();
            BufferedReader reader = new BufferedReader(new InputStreamReader(c.getInputStream()));
            String line;
            while ((line = reader.readLine()) != null) {
                response.append(line);
            }

            return response.toString();
        } catch (MalformedURLException e) {
            e.printStackTrace();
        } catch (ProtocolException e) {
            e.printStackTrace();
        } catch (IOException e) {

        }

        return null;
    }
}

用法:

new ImageUploader(pictureFile, "sample.jpg"){
    @Override
    protected void onPostExecute(String s) {
        super.onPostExecute(s);
        Toast.makeText(getApplicationContext(), s, Toast.LENGTH_LONG).show();
    }
}.execute("http://example/upload.php");

PHP:

<?php
    $file = explode('.', $_FILES['file']['name']);
    $ext = $file[count($file) - 1];
    $name = substr($_FILES['file']['name'], 0, (strlen($ext) + 1) * -1);
    $location = 'images/';
    $cntr = 1;
    $tmp_name = $name;
    if(move_uploaded_file($_FILES['file']['tmp_name'], $location.$tmp_name.'.'.$ext)){
        echo "Image was uploaded.";
    }else{
        echo "Image was not uploaded.";
    }
?>

关于java - 将 Base64 格式的大图片上传到服务器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37561287/

相关文章:

java - 将类类型信息保存到文件以备后用

android - 无法使用 Android Studio 覆盖 view.View 方法

css - 对齐图像 - 水平

css - 使用 nodejs 的 GraphicsMagick 未返回正确的图像

java - 如何在谷歌应用引擎上运行maven项目

java - Freemarker:如何使用 Multimap(或列表 map )

java - 日期格式不会解析字符串

java - 咖啡因:如何得出合适的缓存大小

java - For Loop 遍历数组中的 JSON 对象

iphone - UIEdgeInsets 定位文本/图像问题