I
I
Igor-Novikov2020-02-21 15:11:48
Android
Igor-Novikov, 2020-02-21 15:11:48

How to update View of one RecyclerView item?

There is such a RecyclerView with 3 types of ViewHolder.
5e4fc780e2a62942032957.png
When the screen is flipped, the state of all Switch elements will be reset, and I need to restore it. I saved the states in Bundle(IntegerArrayList), but I can’t figure out how to update the view with the positions of the elements that need to include Switch from the code. There are many examples on the Internet of how you can update the Adapter's data set and then notify, but my data does not change. Tell me where to dig?)

public class UnitSetSelectionFragment extends Fragment implements UnitSetSelectionContract.ViewLearnFragment {

    UnitSetSelectionContract.PresenterLearnFragment mPresenterLearnFragment;

    private static String BUNDLE_KEY = "bundle_key";

    private static int TYPE_SET_WITH_CATEGORY = 1;
    private static int TYPE_SET_WITHOUT_CATEGORY = 2;
    private static int EMPTY_TYPE_SET_WITH_CATEGORY = 3;

    RecyclerView mSetRecyclerView;
    SetsAdapter mAdapter;

    FloatingActionButton startLearnButton;

    Set<Integer> unitSetIdSet = new HashSet<>();

    @Override
    public void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setHasOptionsMenu(true);
        Model model = Lab.get(getContext());
        mPresenterLearnFragment = new UnitSetSelectionFragmentPresenter(model);
        mPresenterLearnFragment.attachView(this);


    }

    @Override
    public void onSaveInstanceState(@NonNull Bundle outState) {
            super.onSaveInstanceState(outState);
            ArrayList<Integer> unitSetIdList = new ArrayList<>();
            for(Integer item : unitSetIdSet){
                unitSetIdList.add(item);
            }
            outState.putIntegerArrayList(BUNDLE_KEY,unitSetIdList);
    }

    @Override
    public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
        super.onCreateOptionsMenu(menu, inflater);
        inflater.inflate(R.menu.learn_menu, menu);
    }

    @Override
    public void onDetach() {
        super.onDetach();
        mPresenterLearnFragment.detachView();
        mPresenterLearnFragment = null;
    }

    @Override
    public void onDestroy() {
        super.onDestroy();
    }


    @SuppressLint("RestrictedApi")
    @Nullable
    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.fragment_learn, container, false);

        mSetRecyclerView = (RecyclerView)view.findViewById(R.id.flow_rw);

        mSetRecyclerView.setLayoutManager(new LinearLayoutManager(getActivity()));

        mPresenterLearnFragment.viewIsReady();

        startLearnButton = view.findViewById(R.id.learnAllSetsButton);
        startLearnButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                BeginExercise();
            }
        });

        if(savedInstanceState!=null){
            ArrayList<Integer> unitSetIdList = new ArrayList<>();
            unitSetIdList = savedInstanceState.getIntegerArrayList(BUNDLE_KEY);
        }

        return view;
    }

    public static UnitSetSelectionFragment newInstance() {
        Bundle args = new Bundle();
        UnitSetSelectionFragment fragment = new UnitSetSelectionFragment();
        fragment.setArguments(args);
        return fragment;
    }

    public void BeginExercise(){

        Intent intent = new Intent(getActivity(), LearnActivity.class);
        ArrayList<Integer> unitSetIdList = new ArrayList<>();
        for(Integer item : unitSetIdSet){
            unitSetIdList.add(item);
        }
        if(unitSetIdList.size()>0) {
            intent.putIntegerArrayListExtra(LEARN_AKTIVITY_KEY_INDEX, unitSetIdList);
            (getActivity()).startActivity(intent);
        }
        else{
            Toast.makeText(getActivity(),"Select sets!",Toast.LENGTH_LONG).show();
        }
    }


    @SuppressLint("RestrictedApi")
    public void UpdateUI(List<UnitSet> unitSetList) {
        List<UnitSet> unitSet = unitSetList;
        mAdapter = new SetsAdapter(unitSet);
        mSetRecyclerView.setAdapter(mAdapter);

        if(unitSet.size()>0) {
            startLearnButton.setVisibility(View.VISIBLE);
        }
    }

    public boolean isFirstWordSetFragmentInFolder(UnitSet unitSet, List<UnitSet> unitSets){
        List<UnitSet> subWordsets = new ArrayList<>();
        int minFolderID;

        //Создание коллекции WordSets с FolderId таким же как и у unitSet.
        for(UnitSet tmpWordset : unitSets){
            if(unitSet.getFolderId() == tmpWordset.getFolderId()){
                subWordsets.add(tmpWordset);
            }
        }

        //Поиск минимального значения. WordSetID не может быть равен нулю. Только у каталогов без категории
        minFolderID = subWordsets.get(0).getUnitSetId();//инициализация первым значением, чтобы было с чем сравнивать.

        for(UnitSet tmpWordset : subWordsets){
            if(tmpWordset.getUnitSetId() < minFolderID){
                minFolderID = tmpWordset.getUnitSetId();
            }
        }

        if (unitSet.getUnitSetId() > minFolderID) {
            return false;
        }

        else {
            return true;
        }
    }



    private class SetsAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder>{

        private List<UnitSet> mUnitSets;

        public SetsAdapter(List<UnitSet> unitSet){
            mUnitSets = unitSet;
        }

        @NonNull
        @Override
        public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {

            View view;
            if(viewType==TYPE_SET_WITH_CATEGORY){
                view = LayoutInflater.from(getActivity()).inflate(R.layout.category_item,parent, false);
                return new SetWithCategoryHolder(view);
            }
            if(viewType==EMPTY_TYPE_SET_WITH_CATEGORY){
                view = LayoutInflater.from(getActivity()).inflate(R.layout.empty_category_item,parent, false);
                return new EmptySetWithCategoryHolder(view);
            }
            else{
                view = LayoutInflater.from(getActivity()).inflate(R.layout.category_item_inner, parent, false);
                return new SetWithoutCategoryHolder(view);
            }
        }

        @Override
        public int getItemViewType(int position) {

            if (mUnitSets.get(position).getFolderId()==0&& isFirstWordSetFragmentInFolder(mUnitSets.get(position), mUnitSets)){
                return EMPTY_TYPE_SET_WITH_CATEGORY;
            }

            else if(isFirstWordSetFragmentInFolder(mUnitSets.get(position), mUnitSets)){
                return TYPE_SET_WITH_CATEGORY;
            }

            else{
                return TYPE_SET_WITHOUT_CATEGORY;
            }
        }

        @Override
        public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, final int position) {
            if(getItemViewType(position)==TYPE_SET_WITH_CATEGORY){
                ((SetWithCategoryHolder)holder).bind(mUnitSets.get(position));
            }
            else if(getItemViewType(position)==EMPTY_TYPE_SET_WITH_CATEGORY){
                ((EmptySetWithCategoryHolder)holder).bind(mUnitSets.get(position));
            }
            else{
                ((SetWithoutCategoryHolder)holder).bind(mUnitSets.get(position));
            }
        }

        @Override
        public int getItemCount() {
            return mUnitSets.size();
        }

Answer the question

In order to leave comments, you need to log in

1 answer(s)
D
Denis Zagaevsky, 2020-02-21
@Igor-Novikov

Well, the answer is simple - the data must change. Only what is in the adapter should be displayed in the recycler, this is the source of truth, and it should be one. Then all these problems don't arise.

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question