Значит, я не получаю ошибку или что-то в этом роде. Это реализация, над которой мне трудно работать.
Я сделал стандартное приложение, в котором вы можете искать акции из API и добавлять их в recyclerView. Я также реализовал searchView, чтобы найти какие-либо определенные акции в моем списке recyclerView.
Однако это моя проблема: скажем, я открыл приложение и добавил новую акцию в список из API. Он отлично добавляет акции в список. Однако когда я go захожу в searchView, чтобы найти ту же самую акцию, которую я только что добавил, я не могу найти ее в списке searchView. Фактически, этот определенный запас ТАКЖЕ удаляется из списка recyclerView (где он существовал совершенно прямо перед тем, как я вошел в searchView). Когда я перезапускаю приложение, акции снова появляются в списке recyclerView, и на этот раз я могу получить к нему доступ из списка searchView. Происходит просто странная вещь.
Эта проблема возникает только в том случае, если я пытаюсь найти акцию, которую только что добавил в свой список, и сразу после этого хочу найти ее в searchView. Если я закрою приложение и снова открою, тогда searchView узнает, что запас существует. В противном случае он просто не знает, когда добавляется новая акция.
Пожалуйста, помогите!
Класс адаптера с реализацией фильтра:
public class Adapter extends RecyclerView.Adapter<Adapter.ViewHolder> implements Filterable {
MainActivity mainAct;
List<Stock> stocks;
List<Stock> searchAllStocks;
Adapter(MainActivity ma, List<Stock> stocks) {
this.mainAct = ma;
this.stocks = stocks;
this.searchAllStocks = new ArrayList<>(stocks);
}
@Override
public Filter getFilter() {
return stockFilter;
}
private Filter stockFilter = new Filter() {
//runs on background thread
@Override
protected FilterResults performFiltering(CharSequence constraint) { //charSequence constraint is whatever is typed into search
List<Stock> filteredList = new ArrayList<Stock>(); //list to store only filtered items
if(constraint == null || constraint.length() == 0) { //if nothing in input field
filteredList.addAll(searchAllStocks); //show all stocks on filteredList
}
else { //else get user input and convert into string to filter
String filterPattern = constraint.toString().toLowerCase().trim();
for(Stock item: searchAllStocks) { //for each stock item in
if(item.getName().toLowerCase().contains(filterPattern)) { //add items that match to filteredList
filteredList.add(item);
}
if(item.getSymbol().toLowerCase().contains(filterPattern)) { //add items that match to filteredList
filteredList.add(item);
}
}
}
//returns FilterResults and gets passed to publishResults
FilterResults results = new FilterResults();
results.values = filteredList;
return results;
}
//runs on UI thread
//clears current stock list and adds results of user's search to list
@Override
protected void publishResults(CharSequence constraint, FilterResults results) {
stocks.clear();
stocks.addAll((List)results.values);
notifyDataSetChanged();
}
};
Метод, выполняемый в MainActivity при нажатии кнопки поиска:
//if search button is pressed
if(item.getItemId() == R.id.search) {
//set up new toolbar for searching
searchView = (SearchView)item.getActionView();
searchView.onActionViewExpanded(); //expands search bar
searchView.setImeOptions(EditorInfo.IME_ACTION_DONE); //sets keyboard icon to done after user types
searchView.setQueryHint("Search...");
searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
//does stuff after text submitted
@Override
public boolean onQueryTextSubmit(String query) {
return false;
}
//does stuff in realtime
@Override
public boolean onQueryTextChange(String newText) {
adapter.getFilter().filter(newText);
return true;
}
});
}
Здесь, я думаю, моя проблема
Этот метод вызывается после получения информации из класса AsyncTask
//update Stock list on screen w/ info passed from Async class AsyncStockDownloader
public void updateData(Stock stock) {
boolean flag = false;
//check for duplicate stocks on list
for(int i = 0; i < stocks.size(); i++) {
if(stocks.get(i).getSymbol().equals(stock.getSymbol())) {
//create alertbox
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setMessage(stock.getSymbol() + " is already displayed!");
builder.setTitle("Duplicate Stock");
AlertDialog dialog = builder.create();
dialog.show();
flag = true;
}
}
//if no duplicate then add to list, database, and notify adapter that we changed
if(!flag) {
stocks.add(stock);
db.addStock(stock);
adapter.notifyDataSetChanged();
//problem is here. we need to let searchAllStocks in adapter know when stock is added
//so that searchbar can store new stock into searchAllStocks
}
}
Пожалуйста, дайте мне знать, есть ли еще какой-либо код, который мне нужно опубликовать. Это только отрывки, где, я думаю, проблема может быть ie.
Заранее спасибо, ребята!
---------------- ------------------------редактировать------------------------- -------------
Это метод, вызываемый после получения информации от Asynctask
Я добавил 1 строку код, чтобы попытаться решить проблему: adapter.searchAllStocks.add (...), как предлагали комментарии
Это результаты
//update Stock list on screen w/ info passed from Async class AsyncStockDownloader
public void updateData(Stock stock) {
boolean flag = false;
//check for duplicate stocks on list
for(int i = 0; i < stocks.size(); i++) {
if(stocks.get(i).getSymbol().equals(stock.getSymbol())) {
adapter.searchAllStocks.clear();
//create alertbox
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setMessage(stock.getSymbol() + " is already displayed!");
builder.setTitle("Duplicate Stock");
AlertDialog dialog = builder.create();
dialog.show();
flag = true;
}
}
//if no duplicate then add to list, database, and notify adapter that we changed
if(!flag) {
stocks.add(stock);
adapter.searchAllStocks.add(new Stock(stock.getSymbol(), stock.getName(), stock.getLatestPrice(), stock.getChange(), stock.getChangePercent()));
db.addStock(stock);
adapter.notifyDataSetChanged();
//problem is here. we need to let searchAllStocks in adapter know when stock is added
//so that searchbar can store new stock into searchAllStocks list
}
}
Итак, теперь позвольте мне показать вам, как выглядит мое приложение.
1. Это домашняя страница, на которой я уже добавил 3 акции
2. Я нажал на опцию поиска на панели инструментов, чтобы найти акцию с именем "GOOG"
В фильтруемом списке также показаны 2 акции GOOG, что довольно странно. , Я бы предпочел показать 1, но не знаю, почему это происходит.
3. Это filterList, который отображается после того, как я очищаю весь свой searchBar. Как видите, для каждой бумаги есть дубликат.
4. Теперь, когда я нажимаю кнопку «Назад», чтобы вернуться на главную страницу, у меня остаются все эти повторяющиеся акции из моего отфильтрованного списка. Очевидно, мы не хотим, чтобы
5. Однако, когда я обновляю sh свою домашнюю страницу, я снова получаю свои прекрасные одиночные акции. Я бы хотел, чтобы мои акции отображались как на этой странице после того, как я каждый раз нажимаю кнопку «Назад»
Еще раз спасибо всем!