mutablelivedata在Refrofit完成下载我的数据和更新hashmap后不会返回hashmap对象

vtwuwzda  于 2021-07-03  发布在  Java
关注(0)|答案(1)|浏览(398)

所以,我最近学习了改型,并尝试创建一个应用程序,使用api下载pokemon的详细信息。下面是mainactivity.java类和mainactivityviewmodel.java类的代码。还有其他类,但它们主要是模型类,所以我没有提到它们:
主活动.java

import androidx.appcompat.app.AppCompatActivity;
import androidx.lifecycle.ViewModelProvider;

import android.os.Bundle;
import android.widget.Toast;

import com.arpansircar.java.pokemonapplication.R;
import com.arpansircar.java.pokemonapplication.viewmodel.MainActivityViewModel;

public class MainActivity extends AppCompatActivity {

    private MainActivityViewModel mainActivityViewModel;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        mainActivityViewModel = new ViewModelProvider(this).get(MainActivityViewModel.class);
    }

    @Override
    protected void onResume() {
        super.onResume();
        observeRetrofitFailures();

        mainActivityViewModel.downloadMainPokemonData();
        mainActivityViewModel.returnMainDownloadedData().observe(this, resultsPokemonServiceModels ->
                mainActivityViewModel.downloadSelectedPokemonData(resultsPokemonServiceModels));

        mainActivityViewModel.returnDownloadedPokemonData().observe(this, map -> {

        });
    }

    private void observeRetrofitFailures() {
        mainActivityViewModel.returnMainServiceErrorLiveData().observe(this, s ->
                Toast.makeText(MainActivity.this, s, Toast.LENGTH_SHORT).show());

        mainActivityViewModel.returnSelectedPokemonServiceErrorLiveData().observe(this, s ->
                Toast.makeText(this, s, Toast.LENGTH_SHORT).show());
    }
}

mainactivityviewmodel.java

import androidx.lifecycle.LiveData;
import androidx.lifecycle.MutableLiveData;
import androidx.lifecycle.ViewModel;

import com.arpansircar.java.pokemonapplication.model.GetPokemonId;
import com.arpansircar.java.pokemonapplication.model.MainPokemonServiceModel;
import com.arpansircar.java.pokemonapplication.model.ResultsPokemonServiceModel;
import com.arpansircar.java.pokemonapplication.model.SelectedPokemonModel;
import com.arpansircar.java.pokemonapplication.retrofit.MainPokemonRetrofitInstance;
import com.arpansircar.java.pokemonapplication.retrofit.PokemonServiceInterface;

import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Objects;

import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import retrofit2.internal.EverythingIsNonNull;

public class MainActivityViewModel extends ViewModel {

    private MainPokemonServiceModel mainPokemonServiceModel;
    private final Map<String, String> pokemonHashMap = new HashMap<>();
    private final PokemonServiceInterface mainPokemonServiceInterface = MainPokemonRetrofitInstance.getInstance();

    private final MutableLiveData<String> mainServiceErrorLiveData = new MutableLiveData<>();
    private final MutableLiveData<String> selectedPokemonServiceErrorLiveData = new MutableLiveData<>();
    private final MutableLiveData<Map<String, String>> downloadMainPokemonData = new MutableLiveData<>();
    private final MutableLiveData<List<ResultsPokemonServiceModel>> resultsPokemonServiceModelListLiveData = new MutableLiveData<>();

    public void downloadMainPokemonData() {
        Call<MainPokemonServiceModel> mainPokemonServiceModelCall = mainPokemonServiceInterface.getResultsDataFromService();
        mainPokemonServiceModelCall.enqueue(new Callback<MainPokemonServiceModel>() {

            @Override
            @EverythingIsNonNull
            public void onResponse(Call<MainPokemonServiceModel> call, Response<MainPokemonServiceModel> response) {
                if (!response.isSuccessful()) {
                    mainServiceErrorLiveData.postValue(String.valueOf(response.code()));
                    return;
                }

                mainPokemonServiceModel = response.body();
                resultsPokemonServiceModelListLiveData.postValue(Objects.requireNonNull(mainPokemonServiceModel).resultsPokemonServiceModel);
            }

            @Override
            @EverythingIsNonNull
            public void onFailure(Call<MainPokemonServiceModel> call, Throwable t) {
                mainServiceErrorLiveData.postValue(t.getMessage());
            }
        });
    }

    public void downloadSelectedPokemonData(List<ResultsPokemonServiceModel> resultsPokemonServiceModelList) {
        for (ResultsPokemonServiceModel resultsPokemonServiceModel : resultsPokemonServiceModelList) {
            String pokemonId = GetPokemonId.getId(resultsPokemonServiceModel.url);
            Call<SelectedPokemonModel> selectedPokemonModelCall = MainPokemonRetrofitInstance.getInstance().getSelectedPokemonSprite(pokemonId);

            selectedPokemonModelCall.enqueue(new Callback<SelectedPokemonModel>() {
                @Override
                @EverythingIsNonNull
                public void onResponse(Call<SelectedPokemonModel> call, Response<SelectedPokemonModel> response) {
                    if (!response.isSuccessful()) {
                        selectedPokemonServiceErrorLiveData.postValue(String.valueOf(response.code()));
                        return;
                    }

                    SelectedPokemonModel selectedPokemonModel = response.body();
                    String pokemonName = Objects.requireNonNull(selectedPokemonModel).pokemonName;
                    String pokemonSpriteUrl = selectedPokemonModel.pokemonSpriteModel.spriteUrl;
                    pokemonHashMap.put(pokemonName, pokemonSpriteUrl);
                }

                @Override
                @EverythingIsNonNull
                public void onFailure(Call<SelectedPokemonModel> call, Throwable t) {
                    selectedPokemonServiceErrorLiveData.postValue(t.getMessage());
                }
            });
        }

        downloadMainPokemonData.postValue(pokemonHashMap);
    }

    public LiveData<Map<String, String>> returnDownloadedPokemonData() {
        return downloadMainPokemonData;
    }

    public LiveData<List<ResultsPokemonServiceModel>> returnMainDownloadedData() {
        return resultsPokemonServiceModelListLiveData;
    }

    public LiveData<String> returnMainServiceErrorLiveData() {
        return mainServiceErrorLiveData;
    }

    public LiveData<String> returnSelectedPokemonServiceErrorLiveData() {
        return selectedPokemonServiceErrorLiveData;
    }

}

我的主要问题是排队 downloadMainPokemonData.postValue(pokemonHashMap); . 当下载完成时,mutablelivedata对象(出于某种原因)不会被通知这一点,即hashmap不会返回到mainactivity。
我做了一些日志检查,发现这个方法确实被触发了。但是,系统甚至在下载完成之前就退出了该方法。下载完成了,是的。但由于某些原因,它不会将下载的hashmap返回到mainactivity。我认为,这可能是因为reformation提供的enqueue方法是异步的,并且在后台线程中执行所有任务。
有没有人能给我一些提示,告诉我怎么处理这个问题?谢谢!

lztngnrs

lztngnrs1#

selectedPokemonModelCall.enqueue 是异步请求。 downloadMainPokemonData.postValue(pokemonHashMap) 之前打过电话 Response<SelectedPokemonModel> 数据已处理

相关问题