ViewModel - изменить параметр метода при наблюдении LiveData во время выполнения? - PullRequest
0 голосов
/ 17 ноября 2018

Я пытаюсь выяснить MVVM (это очень ново для меня), и я выяснил, как наблюдать LiveData, используя Room и ViewModel. Теперь я столкнулся с проблемой.

У меня есть запрос Room, для которого требуется параметр, и именно так я начинаю наблюдать LiveData в onCreate в MainActivity.

    String color = "red";
    myViewModel.getAllCars(color).observe(this, new Observer<List<Car>>() {
            @Override
            public void onChanged(@Nullable List<Car> cars) {
                adapter.setCars(cars);
            }
        });

Используя этот код, я получаю список «красных» автомобилей и заполняю RecyclerView списком.

Теперь к моему вопросу - есть ли способ изменить переменную color внутри метода getAllCars (например, нажатием кнопки) и заставить наблюдателя вернуть новый список? Если я просто изменяю переменную цвета, ничего не происходит

Ответы [ 2 ]

0 голосов
/ 28 декабря 2018

Кроме ответа @dglozano, один простой способ сделать это - наблюдать color вместо наблюдения list. И на valueChange из color получите новый список.

Пример:

В ViewModel классе сделать это

MutableLiveData<String> myColor = new MutableLiveData<String>();

В Activity сделать это:

button.setOnClickListener(new OnClickListener() {
public void onClick(View v)
{
    myViewModel.myColor.setValue("newColor");
} });

myViewModel.myColor.observe(this, new Observer<String>() {
        @Override
        public void onChanged(@Nullable String newValue) {
           // do this on dedicated thread
           List<Car> updateList = myViewModel.getCarsByColor(newValue)
           // update the RecyclerView
        }
    });

Примечание : 1. Не нужно указывать getCarsByColor() как LiveData. Метод в Dao может вернуть List<Cars> вместо LiveData<List<Cars>>.

2.Не запускайте db-запросы в главном потоке и вызывайте notifyDataSetChanged, чтобы обновить RecyclerView.

0 голосов
/ 17 ноября 2018

Как указано в этом ответе , ваше решение Transformation.switchMap

С Веб-сайт Android для разработчиков:

LiveData switchMap (триггер LiveData , функция > func)

Создает LiveData, назовем его swLiveData, который следует следующему потоку: он реагирует на изменения триггера LiveData, применяет данную функцию к новому значению триггера LiveData и устанавливает результирующие LiveData в качестве «поддержки» LiveData для swLiveData. «Поддержка» LiveData означает, что все события его излучение будет повторно передано swLiveData.

В вашей ситуации это будет выглядеть примерно так:

public class CarsViewModel extends ViewModel {
    private CarRepository mRepository;
    private LiveData<List<Car>> mAllCars;
    private LiveData<List<Car>> mCarsFilteredByColor;
    private MutableLiveData<String> filterColor = new MutableLiveData<String>();

    public CarsViewModel (CarRepository carRepository) {
        super(application);
        mRepository = carRepository;
        mAllCars = mRepository.getAllCars();
        mCarsFilteredByColor = Transformations.switchMap(filterColor,
                                                c -> mRepository.getCarsByColor(c));
    }

    LiveData<List<Car>> getCarsFilteredByColor() { return mCarsFilteredByColor; }
    // When you call this function to set a different color, it triggers the new search
    void setFilter(String color) { filterColor.setValue(color); }
    LiveData<List<Car>>> getAllCars() { return mAllCars; }
}

Поэтому, когда вы вызываете метод setFilter из своего представления, изменение filterColor LiveData вызовет Transformation.switchMap, который вызовет mRepository.getCarsByColor(c)), а затем обновит с результатом запроса mCarsFilteredByColor LiveData. Следовательно, если вы наблюдаете этот список в своем представлении и устанавливаете другой цвет, наблюдатель получает новые данные.

Дайте мне знать, если это сработало.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...