Android-基于微调器选择更新listview不';行不通

Android-基于微调器选择更新listview不';行不通,android,listview,spinner,adapter,android-adapter,Android,Listview,Spinner,Adapter,Android Adapter,虽然在stackoverflow上有很多关于这个主题的问题,但我可以说我已经看完了其中的很多问题,并尝试了不同的方法,但我仍然无法让它发挥作用 我有一个ListView,其中填充了我创建的自定义类的自定义适配器。我还有一个微调器,我正试图用它作为列表的过滤器 这是我的简化代码,我删除了所有与此无关的内容,使其尽可能清晰,并简化了一些变量名: public class OnlineNavActivity extends AppCompatActivity { private ListVi

虽然在stackoverflow上有很多关于这个主题的问题,但我可以说我已经看完了其中的很多问题,并尝试了不同的方法,但我仍然无法让它发挥作用

我有一个ListView,其中填充了我创建的自定义类的自定义适配器。我还有一个微调器,我正试图用它作为列表的过滤器

这是我的简化代码,我删除了所有与此无关的内容,使其尽可能清晰,并简化了一些变量名:

public class OnlineNavActivity extends AppCompatActivity {

    private ListView tourList;
    private ArrayList<Tour> toursData;
    private Spinner filterSpinner;
    private TourAdapter tourAdapter;


    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_tours_online);

        // Set up the spinner
        filterSpinner = (Spinner) findViewById(R.id.country_spinner);
        addItemsToSpinner();
        filterSpinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
            @Override
            public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
                String selectedCountry = (String) parent.getItemAtPosition(position);
                Log.i(LOG_TAG, selectedCountry);
                if (!selectedCountry.equals(Data.ALL_COUNTRIES)) {  // if string does not equal to "All Countries"
                    toursData = Data.listByFilter(selectedCountry);
                }
                else {
                    toursData = Data.dataList;
                }
                tourAdapter = new TourAdapter(getApplicationContext(), toursData);
                tourAdapter.notifyDataSetChanged();
            }

            @Override
            public void onNothingSelected(AdapterView<?> parent) {
                toursData = Data.dataList;
                tourAdapter = new TourAdapter(getApplicationContext(), toursData);
                tourAdapter.notifyDataSetChanged();
            }
        });

        // Assign all of the data to the array at first, will change by filter spinner
        toursData = Data.dataList;

        // Generate the list view
        tourList = (ListView) findViewById(R.id.online_nav_list);
        tourAdapter = new TourAdapter(this ,toursData);
        tourList.setAdapter(tourAdapter);


    }

问题是,每次单击微调器时,您都在创建一个新适配器(在onItemSelected和onNothingSelected方法中创建新的TourAdapter(…),而此适配器未链接到您的列表

在这两种方法中,您应该获取列表已经拥有的适配器(使用tourList.setAdapter进行设置),而不是创建一个新的适配器,在适配器上创建一个在其上设置新元素的方法,并使用notifyDataSetChange更新列表

String selectedCountry = (String) parent.getItemAtPosition(position);
Log.i(LOG_TAG, selectedCountry);
if (!selectedCountry.equals(Data.ALL_COUNTRIES)) {
    toursData = Data.listByFilter(selectedCountry);
} else {
    toursData = Data.dataList;
}
tourAdapter = ((TourAdapter) tourList.getAdapter()).setNewElements(toursData);
tourAdapter.notifyDataSetChanged();
setNewElements应该是适配器中的一个方法,如下所示:

public void setNewElements(List<Tour> newElementsList) {
    this.myElements = newElementsList;
}

谢谢你的评论。我的适配器没有任何“elements”变量。在我的适配器中,我使用super调用超类构造函数。我在适配器中更改的唯一一件事是getView方法(用于膨胀视图)。另外,您编写的方法是无效的。但是,在
tourAdapter=((tourAdapter))tourList….
行中,您似乎将该值分配给了tourAdapter。这似乎是一个问题,我应该如何从这里继续?此外,我尝试通过更改一点适配器来实现此方法(并且不执行赋值),但我得到了一个
索引AutofBoundsException
,不确定这是否是正确的解决方案。您是否可以尝试将代码放在我的第一个解决方案中的“编辑”下的onItemSelected方法?由于您使用var toursData作为数据源来填充列表,因此需要使用新数据更新相同的引用,并使用notifyDataSetChanged()更新列表。我尝试过这样做,但不幸的是,它不起作用,我仍然得到
IndexOutOfBoundsException
。Javiervava,感谢您的帮助。我不知何故想出了一个似乎不太理想的解决方案,但这是我唯一能找到的解决方案。请看原始问题中的“编辑”部分。在我的博客:,阵列适配器上的示例与您要查找的类似。希望对你有所帮助!
public void setNewElements(List<Tour> newElementsList) {
    this.myElements = newElementsList;
}
String selectedCountry = (String) parent.getItemAtPosition(position);
Log.i(LOG_TAG, selectedCountry);
toursData.clear();
if (!selectedCountry.equals(Data.ALL_COUNTRIES)) {
    toursData.addAll(Data.listByFilter(selectedCountry));
}
else {
    toursData.addAll(Data.dataList);
}
tourAdapter.notifyDataSetChanged();