使用Android-Image-Cropper将图像发送到服务器时,使用getCroppedImage()返回NULL

时间:2019-01-06 22:25:20

标签: php android android-volley

我正在使用this Github Android Library裁剪所选的图像。然后将该图像加载到两个CircleImageViews中,然后发送到服务器(PHP)。以后可以通过数据库中的图像URL访问它。实际图像存储在服务器上的文件夹中。

当我在没有库的情况下使用默认的onActivityResult 时,一切正常,但是较大的图像将被翻转。因此,我渴望使用这个库。

如果我尝试打开上传到服务器的文件,这就是我得到的:

Image Error

首先,这是我如何启动CropImage活动:

public void showFileChooser() {
    CropImage.activity()
            .setGuidelines(CropImageView.Guidelines.ON)
            .start(this);
}

这是我的onActivityResult()方法和随后的方法uploadAvatar()。请注意评论说我的位图返回NULL:

 @Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);
    if(requestCode == CropImage.CROP_IMAGE_ACTIVITY_REQUEST_CODE) {
        CropImage.ActivityResult result = CropImage.getActivityResult(data);
        if(resultCode == RESULT_OK) {
            picUri = CropImage.getPickImageResultUri(this, data); //get the image URI
            Log.d(TAG, "CropImage Result URI: "+picUri);

            //THIS RETURNS NULL AND I DON'T KNOW WHY
            bitmap = cropImageView.getCroppedImage(); //Assign the bitmap to the cropImageView

            Picasso.get().load(picUri).into(edit_profile_avatar); //Load it into the CircleImageView
            Picasso.get().load(picUri).into(circle_avatar); //Load it into the DrawerLayout CircleImageView
            uploadAvatar(); //Upload to server (see method)
        } else if (resultCode == CropImage.CROP_IMAGE_ACTIVITY_RESULT_ERROR_CODE) {
            Exception error = result.getError();
            ToastMaker.createLongToast(getApplicationContext(), "Error Cropping Image: "+error);
            Log.d(TAG, "Exception: "+error);
        }
    }
}
public void uploadAvatar() {
    //Progress log to show work being done
    final ProgressDialog progressDialog = new ProgressDialog(EditProfileActivity.this, R.style.Custom_Progress_Dialog);
    progressDialog.setIndeterminate(true);
    progressDialog.setMessage("Doing Stuff...");
    progressDialog.show();
    StringRequest stringRequest = new StringRequest(Request.Method.POST, uploadAvatarUrl, new Response.Listener<String>() {
        @Override
        public void onResponse(String response) {
            try {
                Log.d(TAG, "Volley Response: "+response);
                ToastMaker.createLongToast(getApplicationContext(), "Volley Upload Response: "+response);
                uploadArray = new JSONArray(response);
                JSONObject jsonObject = uploadArray.getJSONObject(0);
                String imageString = jsonObject.getString("image");
                Log.d(TAG, "imageString: "+imageString);
                //Picasso.get().load(imageString).into(edit_profile_avatar);
                //Picasso.get().load(imageString).into(circle_avatar);
                progressDialog.dismiss();
            } catch (Exception e) {
                ToastMaker.createLongToast(getApplicationContext(), "Exception: " + e.getMessage());
                progressDialog.dismiss();
            }
        }
    }, new Response.ErrorListener() {
        @Override
        public void onErrorResponse(VolleyError error) {
            ToastMaker.createLongToast(getApplicationContext(), "Volley Error: " + error);
            Log.d(TAG, "VolleyError: " + error);
            progressDialog.dismiss();
        }
    }) {
        @Override
        protected Map<String, String> getParams() {
            Map<String, String> params = new HashMap<>();
            //String imageData = imageToString(bitmap);
            //params.put("image", imageData);
            params.put("image", picUri.toString());
            params.put("username", logged_in_username);
            return params;
        }
    };
    RequestQueue requestQueue = Volley.newRequestQueue(EditProfileActivity.this);
    requestQueue.add(stringRequest);
}

如果您注意到了,我在我的getParams()方法中保留了注释掉的行,这样您就可以看到我使用的原始方法。在这里:

private String imageToString(Bitmap bitmap) {
    ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
    bitmap.compress(Bitmap.CompressFormat.JPEG, 100, outputStream);
    byte[] imageBytes = outputStream.toByteArray();

    return Base64.encodeToString(imageBytes, Base64.DEFAULT);
}

如果我尝试在新的CropImageView位图上使用该方法,则会收到NullPointerException。

这是处理它的简短PHP脚本。请记住,它在使用此CropImage库之前有效。

<?php

include '../../../config/DB.php';

try { $db = new DB(); } catch (Exception $e) { $e->getMessage(); }


if($_SERVER['REQUEST_METHOD'] === 'POST') {

    //Get the username for query
    $username = $_POST['username'];
    //Get the image
    $image = $_POST['image'];
    //Define upload path
    $target_dir = '../../users/'.$username.'/uploads';

    //Delete all other files
    $files = glob('../../users/'.$username.'/uploads/*');
    foreach($files as $file) {
        if(is_file($file)) {
            unlink($file);
        }
    }

    //Create random number + timestamp for new name
    $imageID = rand().'_'.time();
    $target_dir = $target_dir .'/'.$imageID.'.jpg';
    $db_dir = '../users/'.$username.'/uploads/'.$imageID.'.jpg';

    //To see what data is returned
    $user_info = array();

    //If upload is successful, put the path in the database
    if(file_put_contents($target_dir, base64_decode($image))) {
        $user_info[] = array('image'=>$db_dir);
        $insert = $db->updateRow('UPDATE users SET avatar=? WHERE username=?', [$db_dir, $username]);
        echo json_encode($user_info);
    } else {
        echo json_encode('Error');
    }
}

这是写入数据库的内容:

id | username | avatar
 1 | username | ../users/username/uploads/2132273469_1546812127.jpg

最后,这是我的日志中返回的内容:

CropImage Result URI: file:///storage/emulated/0/Android/data/com.companyname.appname/cache/pickImageResult.jpeg
Volley Response: [{"image":"..\/users\/username\/uploads\/2132273469_1546812127.jpg"}]

有人使用过这个库吗?我在这里想念什么?该文档没有显示有关上传到服务器的任何信息,仅将ImageView设置为位图(有效)。

1 个答案:

答案 0 :(得分:0)

好的。我需要从onActivityResult获取URI,并将其分配给Bitmap。这就是为什么它返回null的原因。

这是我的新onActivityResult:

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);
    if(requestCode == CropImage.CROP_IMAGE_ACTIVITY_REQUEST_CODE) {
        Log.d(TAG, "REQUEST CODE: "+requestCode);
        CropImage.ActivityResult result = CropImage.getActivityResult(data);
        if(resultCode == RESULT_OK) {
            try {

                //THIS FIXED IT. NO MORE NULL!
                picUri = result.getUri();
                bitmap = MediaStore.Images.Media.getBitmap(this.getContentResolver(), picUri);
            } catch(Exception e) {
                ToastMaker.createLongToast(getApplicationContext(), "Exception: "+e.getMessage());
            }
            edit_profile_avatar.setImageBitmap(bitmap);
            circle_avatar.setImageBitmap(bitmap);
            uploadAvatar(); 
        } else if (resultCode == CropImage.CROP_IMAGE_ACTIVITY_RESULT_ERROR_CODE) {
            Exception error = result.getError();
            ToastMaker.createLongToast(getApplicationContext(), "Error Cropping Image: "+error);
            Log.d(TAG, "Exception: "+error);
        }
    }
}

图像已成功加载到CircleImageView中,被发送到服务器,并正确显示在相应用户的目录中。

它在数据库中也显示得很好:

 mysql> select id, username, avatar from users;
+----+------------------+-------------------------------------------------------+
| id | username         | avatar                                                |
+----+------------------+-------------------------------------------------------+
|  1 | username         | ../users/username/uploads/1041075557_1546817783.jpeg  |