Данные, назначенные ArrayList в конструкторе, теряют свои данные, несмотря на то, что они нигде не очищаются - PullRequest
1 голос
/ 24 апреля 2020

У меня странная проблема. У меня есть RecyclerAdapter, который имеет два конструктора. Я использую этот же адаптер для заполнения двух RecyclerViews, которые я хочу выглядеть одинаково, но они немного отличаются, и они в двух разных фрагментах. Отсюда два конструктора:

public FinderRecycleAdapter(Context context, ArrayList<String> data) {
    this.mInflater = LayoutInflater.from(context);
    this.mData = data;
    this.mContext = context;
    groupsHidden = new ArrayList<>();

}

public FinderRecycleAdapter(Context context, ArrayList<String> data, ArrayList<String> userEnteredWords) {
    this.mInflater = LayoutInflater.from(context);
    this.mData = data;
    this.mContext = context;
    this.userEnteredWords = userEnteredWords;
    groupsHidden = new ArrayList<>();
}

Во-вторых, я сталкиваюсь с проблемами. Все отображается и работает. RecyclerView отобразит список слов. Пользователь введет некоторые этих слов - все, что я пытаюсь сделать, это изменить цвет слов, которые есть в списке, который ввел пользователь (это не проблема). эти слова передаются и присваиваются ArrayList<string>, это делается успешно, как можно увидеть здесь:

enter image description here

Однако, когда дело доходит до изменения цвет этих слов, при этом в onBindViewHolder этот список теперь пуст:

enter image description here

, несмотря на то, что этот список больше нигде не изменялся.

Вот все употребления этого списка. Строки одна 102-103 - это строки на изображении выше, а строка 43 выше в коде конструктора.

enter image description here

Что странно, this.mData (также ArrayList<string>) используется везде this.userEnteredWords, но this.mData сохраняет свои значения.

Вот весь код onBindViewHolder, но большая часть того, что, я думаю, вам нужно увидеть в onBindViewHolder, представлена ​​на втором изображении.

 // binds the data to the TextView in each row
@Override
public void onBindViewHolder(ViewHolder holder, int position) {
    String word = mData.get(position);
    holder.wordRow.setText(word);

    if (holder.wordRow.getText().toString().matches((".*\\d.*"))) {
        int checkHeaderNum = Integer.parseInt(holder.wordRow.getText().toString().replaceAll("\\D+", ""));

        holder.wordRow.setBackgroundColor(this.mContext.getResources().getColor(R.color.colorPrimary));
        holder.wordRow.setTextColor(this.mContext.getResources().getColor(R.color.white));
        holder.wordRow.setTextSize(25);
        holder.wordRow.setBackground(ContextCompat.getDrawable(mContext, R.drawable.textview_rounded));
        if (this.groupsHidden.contains(checkHeaderNum)) {
            holder.wordRow.setCompoundDrawablesRelativeWithIntrinsicBounds(R.drawable.ic_maximize_white_24dp, 0, R.drawable.ic_maximize_white_24dp, 0); //Inserts the maximizes symbol to the end of TextRow
        } else {
            holder.wordRow.setCompoundDrawablesRelativeWithIntrinsicBounds(R.drawable.ic_minimize_white_24dp, 0, R.drawable.ic_minimize_white_24dp, 0); //Inserts the minimised symbol to the end of TextRow
        }
        holder.wordRow.setPadding(20, 0, 20, 0);

    } else {
        //Resets anything previously made as any attributes previously made will still hold unless reset here
        holder.wordRow.setBackgroundColor(this.mContext.getResources().getColor(R.color.white));
        holder.wordRow.setTextColor(this.mContext.getResources().getColor(R.color.browser_actions_text_color));
        holder.wordRow.setBackgroundResource(0);
        holder.wordRow.setTextSize(22);
        holder.wordRow.setCompoundDrawablesRelativeWithIntrinsicBounds(0, 0, 0, 0);
        holder.wordRow.setPadding(20, 0, 20, 0);

        //Highlighting the letters the user has given if a condition was set -  only for home fragment
        if (isCondition()) {
            int startingIndex = word.indexOf(getUsersLetterEntry());
            int endingIndex = getUsersLetterEntry().length() + startingIndex;

            final SpannableStringBuilder str = new SpannableStringBuilder(word);
            str.setSpan(
                    new ForegroundColorSpan(ContextCompat.getColor(mContext, R.color.blue)), //Making selection colored
                    startingIndex,
                    endingIndex,
                    SpannableStringBuilder.SPAN_EXCLUSIVE_EXCLUSIVE
            );
            str.setSpan(new StyleSpan(Typeface.BOLD), startingIndex, endingIndex, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE); //Making selection bold
            holder.wordRow.setText(str);
        }


        //Setting the user entered words for the letter game to blue. This is only populated if has been called from the LettersGame fragment
        if (this.userEnteredWords != null && this.userEnteredWords.size() > 0) {
            if (this.userEnteredWords.contains(holder.wordRow.getText().toString())) {
                holder.wordRow.setTextColor(this.mContext.getResources().getColor(R.color.blue));
                holder.wordRow.setTypeface(Typeface.DEFAULT_BOLD);
            }
        }


    }

Я что-то упускаю из виду совершенно очевидно? Я не сталкивался с этим раньше.

1 Ответ

1 голос
/ 25 апреля 2020

Ваш конструктор не копирует данные, он просто сохраняет тот же ArrayList, который был передан. Поэтому, если этот ArrayList, который доступен за пределами вашего объекта, будет изменен позже, изменения также будут отражены в ArrayList вашего объекта, поскольку это один и тот же объект.

Я бы предложил создать новый ArrayList и затем использовать Collections.addAll

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