简体   繁体   English

Recyclerview 项目中的多个微调器

[英]Multiple Spinner in a Recyclerview item

I have a recycler view with 11-row data items.我有一个包含 11 行数据项的回收站视图。 I need to fix two spinners in each row.我需要在每行修复两个微调器。 That the second spinner data should be dependent on the first Spinner data changes.即第二个 Spinner 数据应该依赖于第一个 Spinner 数据的变化。 While I'm making new entry data loaded correctly.虽然我正在正确加载新的条目数据。 When I came to edit the first spinner data loading correctly done and already existing data was fixed correctly.当我开始编辑第一个微调器数据时,加载正确完成并且已经存在的数据被正确修复。 But in the second spinner, it shows the data of the last loaded item.但是在第二个微调器中,它显示了最后加载的项目的数据。 ie Last row (11th row) spinner data has been set in all the second spinners.即在所有第二个微调器中设置了最后一行(第 11 行)微调器数据。 How to solve this?如何解决这个问题?

Shown below code is under onBindViewHolder() method in recyclerViewAdapter下面显示的代码位于 recyclerViewAdapter 中的 onBindViewHolder() 方法下


 fortnightLookupList = gCache.getFortNightLookup();



        for(int i = 0; i<fortnightLookupList.size(); i++){
            funtioningSpinnerList.add(fortnightLookupList.get(i).getFunctioning());
        }
reasoningAdapter =
    new ArrayAdapter<>(thisActivity, android.R.layout.simple_spinner_item, funtioningSpinnerList);
reasoningAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
holder.functioningSpinner.setAdapter(reasoningAdapter);

if (entryStatus.equals(Constants.NEW)) {
    holder.functioningSpinner.setOnItemSelectedListener(new AdapterView . OnItemSelectedListener () {
        @Override
        public void onItemSelected(AdapterView<?> parent, View view, int pos, long id) {
            if (pos > 0) {
                remoteLocationEntryModelData.get(position).checkList =
                    funtioningSpinnerList.get(pos);
                //loadScoreSpinner(funtioningSpinnerList.get(pos), holder, position);

                scoreList.clear();

                for (int i = 0; i < fortnightLookupList.size(); i++) {
                    if (fortnightLookupList.get(i).getFunctioning().equals(funtioningSpinnerList.get(pos)) ) {
                        scoreList.add(fortnightLookupList.get(i).getScore());
                    }
                }

                scoreAdapter =
                    new ArrayAdapter<>(thisActivity, android.R.layout.simple_spinner_item, scoreList);
                scoreAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
                holder.scoreSpinner.setAdapter(scoreAdapter);

            } else {
                remoteLocationEntryModelData.get(position).checkList = "$";
                scoreList.clear();
                scoreList.add(0, "---- select ----");
                scoreAdapter =
                    new ArrayAdapter<>(thisActivity, android.R.layout.simple_spinner_item, scoreList);
                scoreAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
                holder.scoreSpinner.setAdapter(scoreAdapter);
            }
        }

        @Override
        public void onNothingSelected(AdapterView<?> parent) {

        }
    });

} else if (entryStatus.equals(Constants.EDIT)) {

    if (!TextUtils.isEmpty( String.valueOf( editList.getDescriptions().get(position).getLogId() ) ) ) {
        remoteLocationEntryModelData.get(position).logId =
            editList.getDescriptions().get(position).getLogId();
    }

    if (!TextUtils.isEmpty(editList.getDescriptions().get(position).getRemarks())) {
        holder.remarksEdt.setText(editList.getDescriptions().get(position).getRemarks());
    }



    holder.functioningSpinner.setSelection(
        funtioningSpinnerList.indexOf(
            editList.getDescriptions().get(position).getCheckList()
        )
    );

    holder.functioningSpinner.setOnItemSelectedListener(new AdapterView . OnItemSelectedListener () {
        @Override
        public void onItemSelected(AdapterView<?> parent, View view, int pos, long id) {
            if (pos > 0) {
                remoteLocationEntryModelData.get(position).checkList =
                    funtioningSpinnerList.get(pos);
                //loadScoreSpinner(funtioningSpinnerList.get(pos), holder, position);

                scoreList.clear();

                for (int i = 0; i < fortnightLookupList.size(); i++) {
                    if (fortnightLookupList.get(i).getFunctioning()
                            .equals(funtioningSpinnerList.get(pos))
                    ) {
                        scoreList.add(fortnightLookupList.get(i).getScore());
                    }
                }

                scoreAdapter =
                    new ArrayAdapter<>(thisActivity, android.R.layout.simple_spinner_item, scoreList);
                scoreAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
                holder.scoreSpinner.setAdapter(scoreAdapter);

                //holder.scoreSpinner.setSelection(scoreList.indexOf(editList.getDescriptions().get(position).getScore()));

            } else {
                remoteLocationEntryModelData.get(position).checkList = "$";
                scoreList.clear();
                scoreList.add(0, "---- select ----");
                scoreAdapter =
                    new ArrayAdapter<>(thisActivity, android.R.layout.simple_spinner_item, scoreList);
                scoreAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
                holder.scoreSpinner.setAdapter(scoreAdapter);
            }
        }

        @Override
        public void onNothingSelected(AdapterView<?> parent) {

        }
    });
}

Note While I debug it step by step it is working correctly, but not when during run注意虽然我逐步调试它,但它工作正常,但在运行期间却没有

Current Output当前Output 在此处输入图像描述

Expected Output预计 Output

在此处输入图像描述

You save scoreList in a global variable and never redefines this value您将scoreList保存在全局变量中,并且从不重新定义此值

In holder.functioningSpinner.setOnItemSelectedListener you makes scoreList.clear()holder.functioningSpinner.setOnItemSelectedListener你做scoreList.clear()

with always same line you set same List reference to all adapters in new ArrayAdapter<>(thisActivity, android.R.layout.simple_spinner_item, scoreList)始终在同一行中为new ArrayAdapter<>(thisActivity, android.R.layout.simple_spinner_item, scoreList)中的所有适配器设置相同List引用

with scoreList.clear() you removes data in all adapters and adds new values.使用scoreList.clear()可以删除所有适配器中的数据并添加新值。

=> is the reason, why you see the data of last item in all list items => 是原因,为什么您会在所有列表项中看到最后一项的数据

Note While I debug it step by step it is working correctly, but not when during run注意虽然我逐步调试它,但它工作正常,但在运行期间却没有

Reason for it is:原因是:

  • in debug mode you are slow .在调试模式下你很 there everything comes step by step.一切都是一步一步来的。
  • in real execution everything happens in some milliseconds在实际执行中,一切都在几毫秒内发生

HOW TO SOLVE怎么解决

Possibility 1. recreate the list instead of clear data.可能性 1. 重新创建列表而不是清除数据。 You make already always new ArrayAdapter , why you store scoreList instance globally?您已经创建了new ArrayAdapter ,为什么要全局存储scoreList实例?

Possibility 2. Make a holder as own class and everything you do in onBindViewHolder make in a holder class.可能性 2. 将持有人作为自己的 class 并且您在onBindViewHolder中所做的一切都在持有人 class 中进行。

Example:例子:

generate base holder class生成底座支架 class

public abstract class BaseRecyclerBindingHolder<Item> extends RecyclerView.ViewHolder {

    public BaseRecyclerBindingHolder(View itemView) {
        super(itemView);
    }

    public abstract void configureView(Item item);
}

and base adapter class和基本适配器 class

public abstract class BaseRecyclerBindingAdapter<Item, Holder extends BaseRecyclerBindingHolder<? super Item>, ItemBinding extends ViewBinding>
        extends RecyclerView.Adapter<Holder> {

    // Store a member variable for the items
    protected final List<Item> mItems;

    /**
     * @param items adapter items to show in UI
     */
    public BaseRecyclerBindingAdapter(List<Item> items) {
        mItems = items;
    }

    /**
     * Usually involves inflating a layout from XML and returning the holder
     *
     * @param parent   container of adapter items
     * @param viewType type of item
     * @return ViewHolder for adapter item
     */
    @NonNull
    @Override
    public Holder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
        // Inflate the custom layout
        ItemBinding itemView = getLayoutResource(LayoutInflater.from(parent.getContext()), parent);

        return getHolder(itemView, viewType);
    }

    /**
     * Involves populating data into the item through holder
     *
     * @param holder   ViewHolder class to construct UI for item
     * @param position item position in adapter
     */
    @Override
    public void onBindViewHolder(@NonNull Holder holder, int position) {
        Item item = mItems.get(position);

        holder.configureView(item);
    }

    /**
     * @return count of items in adapter
     */
    @Override
    public int getItemCount() {
        return mItems.size();
    }

    /**
     * gets the type of item of specified position in adapter
     *
     * @param position item position
     * @return default 0
     */
    @Override
    public abstract int getItemViewType(int position);

    /**
     * Usually use:
     * ItemBinding.inflate(layoutInflater);
     * To use parents properties of width and height, make this way:
     * ItemBinding.inflate(layoutInflater, parent, false);
     *
     * @param layoutInflater the inflater to set XMl to view
     * @param parent         container of adapter items
     * @return ViewBinding element with access to all views with IDs in UI
     */
    protected abstract ItemBinding getLayoutResource(LayoutInflater layoutInflater, ViewGroup parent);

    /**
     * based on viewType gets the ViewHolder class for the item
     *
     * @param viewBinding element with access to all views with IDs in UI
     * @param viewType    type of item
     * @return ViewHolder for adapter item
     */
    protected abstract Holder getHolder(ItemBinding viewBinding, int viewType);

    /**
     * @param position item position
     * @return item on specified position in adapter
     */
    public Item getItem(int position) {
        return mItems.get(position);
    }

    /**
     * @return list of items in adapter
     */
    public List<Item> getItems() {
        return mItems;
    }
}

now generate specific holder for your purpose现在为您的目的生成特定的持有人

public class YourHolderName extends BaseRecyclerBindingHolder<YourHolderItem> {

    private final YourHolderBinding binding;

    // add here more variable that you needs from adapter
    public YourHolderName(YourHolderBinding binding) {
        super(binding.getRoot());

        this.binding = binding;
    }

    @Override
    public void configureView(YourHolderItem yourHolderItem) {
        // here comes what you make i your holder
    }
}

and at least define adapter that is always super easy and small并且至少定义总是超级简单和小巧的适配器

public class YourAdapterName extends BaseRecyclerBindingAdapter<YourHolderItem, YourHolderName, YourHolderBinding> {

    /**
     * @param yourHolderItem adapter items to show in UI
     */
    // add more parameters if needed
    public YourAdapterName(List<YourHolderItem> yourHolderItems) {
        super(yourHolderItems);
    }

    @Override
    public int getItemViewType(int position) {
        return 0;
    }

    @Override
    protected YourHolderBinding getLayoutResource(LayoutInflater layoutInflater, ViewGroup parent) {
        return YourHolderBinding.inflate(layoutInflater, parent, false);
    }

    @Override
    protected YourHolderName getHolder(YourHolderBinding viewBinding, int viewType) {
        // add more parameters if needed
        return new YourHolderName(viewBinding);
    }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 当用户在微调器中选择项目时如何在项目回收视图中设置图像 - how to set image in item recyclerview when user choose a item in spinner 更改微调器项目数据时更新recyclerview单行数据 - Update recyclerview single row data when spinner item data is changed 刷新ArrayList以使用Click on Spinner Item将新数据显示到RecyclerView中 - Refresh ArrayList to show new Data into RecyclerView using Click on Spinner Item 如何基于微调项选择在recyclerview中应用过滤器? - How to apply filter in recyclerview based on spinner item selection? 如何通过微调器项 position、Android、Z93F725A074233FE1C886F448B 过滤带有 ArrayList 的 RecyclerView - How to filter RecyclerView with ArrayList by spinner item position, Android, java? 如何处理多个微调框选择项的比较? - How to handle multiple spinner selected item comparison? 单击recyclerview上的项目时的多个数据 - Multiple data when clicked item on recyclerview 如何在 RecyclerView 列表项中显示多个 TextView - How to display multiple TextViews in a RecyclerView list item Recyclerview项目中的Android recyclerview - Android recyclerview in a recyclerview item Android - 如何在一个活动中禁用多个微调器的特定项目 - Android - How to Disable Specific Item for Multiple Spinner in One Activity
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM