Android - Retrofit: Не грузит изображения на сервер

286
09 января 2018, 14:17

Создал приложение, которое грузит изображения на сервер, использую библиотеку Retrofit.

Layout файл:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context="com.example.haykmkrtchyan.retrofitimageupload.MainActivity">
<ImageView
    android:id="@+id/imageView"
    android:layout_width="300dp"
    android:layout_height="250dp"
    android:layout_gravity="center_horizontal"
    android:layout_marginTop="15dp"
    android:contentDescription="@string/Image"
    android:visibility="gone" />
<EditText
    android:id="@+id/img_title"
    android:layout_width="match_parent"
    android:layout_height="50dp"
    android:layout_marginTop="20dp"
    android:hint="@string/Title"
    android:visibility="gone" />
<Button
    android:id="@+id/chooseBtn"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_marginLeft="50dp"
    android:layout_marginRight="50dp"
    android:layout_marginTop="25dp"
    android:text="@string/Choose" />
<Button
    android:id="@+id/uploadBtn"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_marginLeft="50dp"
    android:layout_marginRight="50dp"
    android:layout_marginTop="15dp"
    android:enabled="false"
    android:text="@string/Upload" />

Есть 3 класса и 1 интерфейс.

ApiClient.java:

public class ApiClient {
private static final String BaseURL = "http://10.0.2.2/imageupload/";
private static Retrofit retrofit;
public static Retrofit getApiClient() {
    if (retrofit == null) {
        retrofit = new Retrofit.Builder()
                .baseUrl(BaseURL)
                .addConverterFactory(GsonConverterFactory.create())
                .build();
    }
    return retrofit;
}
}

ImageClass.java:

public class ImageClass {
@SerializedName("title")
private String Title;
@SerializedName("image")
private String Image;
@SerializedName("response")
private String Response;
public String getResponse() {
    return Response;
}
}

ApiInterface.java:

public interface ApiInterface {
@FormUrlEncoded
@POST("upload.php")
Call<ImageClass> uploadImage(@Field("title") String title, @Field("image") String image);

}

MainActivity.java:

public class MainActivity extends AppCompatActivity implements View.OnClickListener {
private EditText title;
private Button choose, upload;
private ImageView image;
private static final int IMG_REQUEST = 777;
private Bitmap bitmap;
@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    title = findViewById(R.id.img_title);
    choose = findViewById(R.id.chooseBtn);
    upload = findViewById(R.id.uploadBtn);
    image = findViewById(R.id.imageView);
    choose.setOnClickListener(this);
    upload.setOnClickListener(this);
}
@Override
public void onClick(View view) {
    switch (view.getId()) {
        case R.id.chooseBtn:
            selectImage();
            break;
        case R.id.uploadBtn:
            uploadImage();
            break;
    }
}
private void selectImage() {
    Intent intent = new Intent();
    intent.setType("image/*");
    intent.setAction(Intent.ACTION_GET_CONTENT);
    startActivityForResult(intent, IMG_REQUEST);
}
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);
    if (requestCode == IMG_REQUEST && resultCode == RESULT_OK && data != null) {
        Uri path = data.getData();
        try {
            bitmap = MediaStore.Images.Media.getBitmap(getContentResolver(), path);
            image.setImageBitmap(bitmap);
            image.setVisibility(View.VISIBLE);
            title.setVisibility(View.VISIBLE);
            choose.setEnabled(false);
            upload.setEnabled(true);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}
private void uploadImage() {
    String Image = imageToString();
    String Title = title.getText().toString();
    ApiInterface apiInterface = ApiClient.getApiClient().create(ApiInterface.class);
    Call<ImageClass> call = apiInterface.uploadImage(Title, Image);
    call.enqueue(new Callback<ImageClass>() {
        @Override
        public void onResponse(@NonNull Call<ImageClass> call, @NonNull Response<ImageClass> response) {
            ImageClass imageClass = response.body();
            Toast.makeText(MainActivity.this, "Server Response: " + imageClass, Toast.LENGTH_SHORT).show();
            image.setVisibility(View.GONE);
            title.setVisibility(View.GONE);
            choose.setEnabled(true);
            upload.setEnabled(false);
            title.setText("");
        }
        @Override
        public void onFailure(@NonNull Call<ImageClass> call, @NonNull Throwable t) {
        }
    });
}
private String imageToString(){
    ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
    bitmap.compress(Bitmap.CompressFormat.JPEG, 100, outputStream);
    //bitmap.compress(Bitmap.CompressFormat.PNG, 100, outputStream);
    byte[] imgByte = outputStream.toByteArray();
    return Base64.encodeToString(imgByte, Base64.DEFAULT);
}
}

Есть 2 кнопки, 1 на выбор картинки, а 2 для отправки на сервер. Сервер написан руками, там все работает. Но когда нажимаю на отправку, то происходит краш - проблема с памятью.

Как решить проблему?

Вот логи:

01-07 14:25:10.142 3684-3684/? E/memtrack: Couldn't load memtrack module (No such file or directory)
01-07 14:25:10.142 3684-3684/? E/android.os.Debug: failed to load memtrack module: -2
01-07 14:25:11.674 3704-3704/? E/memtrack: Couldn't load memtrack module (No such file or directory)
01-07 14:25:11.674 3704-3704/? E/android.os.Debug: failed to load memtrack module: -2
01-07 14:25:11.830 3714-3714/com.example.haykmkrtchyan.retrofitimageupload E/dalvikvm: Could not find class 'android.graphics.drawable.RippleDrawable', referenced from method android.support.v7.widget.AppCompatImageHelper.hasOverlappingRendering
01-07 14:25:13.302 3714-3714/com.example.haykmkrtchyan.retrofitimageupload E/OpenGLRenderer: Getting MAX_TEXTURE_SIZE from GradienCache
01-07 14:25:13.302 3714-3714/com.example.haykmkrtchyan.retrofitimageupload E/OpenGLRenderer: MAX_TEXTURE_SIZE: 16384
01-07 14:25:13.310 3714-3714/com.example.haykmkrtchyan.retrofitimageupload E/OpenGLRenderer: Getting MAX_TEXTURE_SIZE from Caches::initConstraints()
01-07 14:25:13.314 3714-3714/com.example.haykmkrtchyan.retrofitimageupload E/OpenGLRenderer: MAX_TEXTURE_SIZE: 16384
01-07 14:25:18.298 3714-3714/com.example.haykmkrtchyan.retrofitimageupload E/dalvikvm: Could not find class 'android.support.v4.app.ActivityCompat$SharedElementCallback23Impl', referenced from method android.support.v4.app.ActivityCompat.setEnterSharedElementCallback
01-07 14:25:18.298 3714-3714/com.example.haykmkrtchyan.retrofitimageupload E/dalvikvm: Could not find class 'android.support.v4.app.ActivityCompat$SharedElementCallback21Impl', referenced from method android.support.v4.app.ActivityCompat.setEnterSharedElementCallback
01-07 14:25:18.298 3714-3714/com.example.haykmkrtchyan.retrofitimageupload E/dalvikvm: Could not find class 'android.support.v4.app.ActivityCompat$SharedElementCallback23Impl', referenced from method android.support.v4.app.ActivityCompat.setExitSharedElementCallback
01-07 14:25:18.298 3714-3714/com.example.haykmkrtchyan.retrofitimageupload E/dalvikvm: Could not find class 'android.support.v4.app.ActivityCompat$SharedElementCallback21Impl', referenced from method android.support.v4.app.ActivityCompat.setExitSharedElementCallback
01-07 14:25:46.369 3714-3714/com.example.haykmkrtchyan.retrofitimageupload E/dalvikvm-heap: Out of memory on a 16775180-byte allocation.
01-07 14:25:46.377 3714-3714/com.example.haykmkrtchyan.retrofitimageupload E/dalvikvm-heap: Out of memory on a 8386572-byte allocation.
01-07 14:25:46.381 3714-3714/com.example.haykmkrtchyan.retrofitimageupload E/AndroidRuntime: FATAL EXCEPTION: main
                                                                                             Process: com.example.haykmkrtchyan.retrofitimageupload, PID: 3714
                                                                                             java.lang.OutOfMemoryError
                                                                                                 at java.io.ByteArrayOutputStream.toByteArray(ByteArrayOutputStream.java:122)
                                                                                                 at com.example.haykmkrtchyan.retrofitimageupload.MainActivity.imageToString(MainActivity.java:120)
                                                                                                 at com.example.haykmkrtchyan.retrofitimageupload.MainActivity.uploadImage(MainActivity.java:92)
                                                                                                 at com.example.haykmkrtchyan.retrofitimageupload.MainActivity.onClick(MainActivity.java:55)
                                                                                                 at android.view.View.performClick(View.java:4438)
                                                                                                 at android.view.View$PerformClick.run(View.java:18422)
                                                                                                 at android.os.Handler.handleCallback(Handler.java:733)
                                                                                                 at android.os.Handler.dispatchMessage(Handler.java:95)
                                                                                                 at android.os.Looper.loop(Looper.java:136)
                                                                                                 at android.app.ActivityThread.main(ActivityThread.java:5001)
                                                                                                 at java.lang.reflect.Method.invokeNative(Native Method)
                                                                                                 at java.lang.reflect.Method.invoke(Method.java:515)
                                                                                                 at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:785)
                                                                                                 at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:601)
                                                                                                 at dalvik.system.NativeStart.main(Native Method)
01-07 14:25:58.317 2214-2287/system_process E/InputDispatcher: channel '52a6901c PopupWindow:52877f88 (server)' ~ Channel is unrecoverably broken and will be disposed!
01-07 14:25:58.317 2214-2287/system_process E/InputDispatcher: channel '529e00c4 com.example.haykmkrtchyan.retrofitimageupload/com.example.haykmkrtchyan.retrofitimageupload.MainActivity (server)' ~ Channel is unrecoverably broken and will be disposed!

Некоторое время назад краш не происходил, но и на сервер не отправлял. Нажал отправить, происходит freeze на 5-10 секунд и ничего, как был так и остался.

READ ALSO
Ошибка компиляции Collections.synchronizedList: synchronizedList (java.util.List&lt;T&gt;) in Collections&#160;cannot be applied to java.util.ArrayLis

Ошибка компиляции Collections.synchronizedList: synchronizedList (java.util.List<T>) in Collections cannot be applied to java.util.ArrayLis

Пишу клиент — серверное приложениеДля учета подключившихся клиентов хочу использовать ArrayList

165
Отсортировать массив в JAVA (цифры + текст)

Отсортировать массив в JAVA (цифры + текст)

Как отсортировать массив по числам, которые идут перед URlДопустим есть данные:

272
Ajax отправка POST запроса на сервлет (Java)

Ajax отправка POST запроса на сервлет (Java)

Проблема следующаяЕсть сервлет на сервере, который принимает данные в формате json

197
Изменить context проекта Spring

Изменить context проекта Spring

Изменяю context-root проекта через properties->Web Project Settings с training на SpringMVCНо приложение всё равно работает только по этому адресу, почему?

165