Итак, в настоящее время я беру изображение и обновляю его в RecyclerView
с использованием намерения камеры:
private void cameraIntent() {
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
if (takePictureIntent.resolveActivity(getActivity().getPackageManager()) != null) {
File photoFile = null;
try {
photoFile = createImageFile();
} catch (IOException ex) {
Log.e(TAG, ex.getLocalizedMessage());
}
if (photoFile != null) {
Uri uri = FileProvider.getUriForFile(getActivity().getApplicationContext(),
"packagename.fileprovider",
photoFile);
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, uri);
startActivityForResult(takePictureIntent, REQUEST_TAKE_PHOTO);
}
}
}
Что произойдет до этого, это вызовет намерение из setOnItemClickListener interface
, которое я создал в моем RecyclerView.Adapter
, который вызывается в onCreate
, для заполнения данных с веб-сервера (или при срабатывании setVisibleUserHint
, поскольку они снова вводят фрагмент).
//данные об объекте камеры
if (isCamera) {
cameraArray = object.getJSONArray(PROFILE_DETAILS_CAMERA_ARRAY_KEY);
sortAdapter(true, object, cameraArray);
} else {
galleryArray = object.getJSONArray(PROFILE_DETAILS_GALLERY_ARRAY_KEY);
sortAdapter(false, object, galleryArray);
}
//адаптеры настроек
cameraAdapter = new RecyclerViewAdapterGallery(getActivity(), array, true);
cameraAdapter.setOnItemClickListener(new RecyclerViewAdapterGallery.onItemClickListener() {
@Override
public void setOnItemClickListener(View view, final int position, String image, final boolean isCamera, boolean isLongClick) {
clickResponse(view, position, image, isCamera, isLongClick, cameraAdapter, array, object);
}
});
recyclerView.setAdapter(cameraAdapter);
cameraAdapter.notifyDataSetChanged();
Что происходит в столбце onActivityResult
:
@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
switch (requestCode) {
case REQUEST_TAKE_PHOTO:
if (resultCode != Activity.RESULT_CANCELED) {
if (resultCode == Activity.RESULT_OK) {
try {
handleBigCameraPhoto(finalPosition);
} catch (IOException e) {
Log.e(TAG, e.getLocalizedMessage());
}
}
}
break;
...
}
}
handleBigCameraPhoto:
private void handleBigCameraPhoto(int position) {
Intent mediaScanIntent = new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE);
File f = new File(mCurrentPhotoPath);
Uri contentUri = Uri.fromFile(f);
mediaScanIntent.setData(contentUri);
getActivity().sendBroadcast(mediaScanIntent);
saveFile(f, false, position);
}
Это прекрасно работает, он сохраняет файл на веб-сервере, но я хочу обновить адаптер, когда это будет успешным, и, конечно, я не могу восстановить объект адаптера с помощью outState
или inState
bundle.
cameraArray.put(position, parseFile.getUrl());
userObject.put(PROFILE_DETAILS_CAMERA_ARRAY_KEY, cameraArray);
userObject.saveInBackground(new SaveCallback() {
@Override
public void done(ParseException e) {
if (e == null) {
if (cameraAdapter != null) {
cameraAdapter.updatePosition(cameraArray, position);
}
} else {
Log.e(TAG, "failed " + e.getLocalizedMessage());
}
}
});
К этому моменту я не уверен, почему cameraAdapter
не обновляется, так как он не возвращает null и вызывает updatePosition().
public void updatePosition(JSONArray array, int position) {
Log.e(TAG, "updatePositionCalled");
this.imageList = array;
notifyItemChanged(position);
}
Если кто-то может помочь мне решить эту тайну, это было бы здорово! Кроме того, если вам нужен еще какой-либо код или проверка вообще, сообщите мне.
Примечание. В настоящее время у меня есть JSONArray
объектов, позиция в объекте адаптера и веб-сервера, хранящаяся в пакете saveInstanceState
, и восстанавливается правильно (потому что, когда я выхожу из ViewPager
и вернитесь, вызывая setUserVisibleHint
, он правильно восстанавливает адаптер с веб-сервера).
Обновление. Я создал метод getImageList()
внутри адаптера и вызвал его после предполагаемого "обновления", обновляя значения списка, но не список! Поэтому я действительно думаю, что проблема связана с notifyItemChanged(position)
public JSONArray getImageList() {
return imageList;
}
//новый вызов
if (e == null) {
cameraAdapter.updatePosition(cameraArray, position);
Log.e(TAG, cameraAdapter.getImageList().toString());
} else {
Log.e(TAG, "failed " + e.getLocalizedMessage());
}
Он буквально печатает соответствующие значения в списке, который был передан адаптеру, но, похоже, не обновляет пользовательский интерфейс.
Обновление II:
У меня было два (теперь удаленных) ответа, которые советовали мне notifyDataSetChanged()
, что не имеет никакого значения вообще и является контрпродуктивным, поскольку он будет перепроверять весь адаптер внутри фрагмента, что делает его медленным. Я уже перевязываю выделенное положение (предположительно) с помощью notifyItemChanged()
.
Примечание II. Я предлагаю щедрость не для ленивых и невосстановленных ответов, но для решения, по крайней мере, объяснения, я хотел бы знать почему это происходит не так, поэтому я снова не сталкиваюсь с той же проблемой (не быстрое решение). Я уже хорошо знаю различные функции и компоненты RecyclerView
, RecyclerView.Adapter
и RecyclerView.ViewHolder
, у меня просто возникают проблемы в этом конкретном сценарии, когда Activity
возвращает результат, но не обновляет UI, как и должно быть.