【问题标题】:Implementing search functionality on ListView在 ListView 上实现搜索功能
【发布时间】:2020-09-15 07:20:45
【问题描述】:

我正在为我的数据库使用解析服务器。我想在用户搜索搜索功能时获取该项目。我在谷歌上搜索了这个,但没有找到合适的。

#MainActivity

  @Override
  public boolean onCreateOptionsMenu(Menu menu) {
    // Inflate the menu; this adds items to the action bar if it is present.
    getMenuInflater().inflate(R.menu.menu_main, menu);
    final ParseQuery<ParseUser> query = ParseUser.getQuery();

    
    //get the search view and set the searchable configuration
    SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
    SearchView searchView = (SearchView) menu.findItem(R.id.search).getActionView();
    //searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));


    //assumes the current activity is the searchable activity
    searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));

    searchView.setSubmitButtonEnabled(true);
     searchView.setSubmitButtonEnabled(true);
   // searchView.setOnQueryTextListener((SearchView.OnQueryTextListener) this);

    searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
        @Override
        public boolean onQueryTextSubmit(String query) {
         
            return false;
        }

        @Override
        public boolean onQueryTextChange(String newText) {

            return true;
        }
    });



    return true;
}


@Override
public boolean onSearchRequested() {

    //pauseSomeStuff();
    return super.onSearchRequested();
}

RoomCardRecyclerViewAdapter

我想通过使用搜索功能从这个适配器中获取项目并为用户过滤它

private List<ParseObject> mRooms = new ArrayList<>();
private ParseObject room;
private String mSection;

public RoomCardRecyclerViewAdapter(){
    super(DIFF_CALLBACK);
}
public static final DiffUtil.ItemCallback<ParseObject>  DIFF_CALLBACK = new 
DiffUtil.ItemCallback<ParseObject>() {
    @Override
    public boolean areItemsTheSame(@NonNull ParseObject oldItem, @NonNull ParseObject newItem) {
        return oldItem.getObjectId() == newItem.getObjectId();
    }

    @Override
    public boolean areContentsTheSame(@NonNull ParseObject oldItem, @NonNull ParseObject newItem) {
        return (oldItem.getUpdatedAt().equals(newItem.getUpdatedAt()) && 
 oldItem.getCreatedAt().equals(newItem.getCreatedAt()));
    }
};


public RoomCardRecyclerViewAdapter(String section) {
  this();
  this.mSection = section;
}
public class RoomViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener{
    protected ImageView mRoomImage;
    protected TextView mRoomPrice;
    protected TextView mInclusiveOrNot;
    protected TextView mPropertyType;
    protected TextView mNumOfBeds;
    protected TextView mNumOfBaths;
    protected TextView mRoomLocation;

    private Context context;

    public RoomViewHolder(Context context, View itemView) {
        super(itemView);
        mRoomImage = itemView.findViewById(R.id.room_image);
        mRoomPrice = itemView.findViewById(R.id.price_label);
        mInclusiveOrNot = itemView.findViewById(R.id.incl_excl_label);
        mPropertyType = itemView.findViewById(R.id.propertyType_label);
        mNumOfBeds = itemView.findViewById(R.id.num_beds_label);
        mNumOfBaths = itemView.findViewById(R.id.details_num_baths_label);
        mRoomLocation = itemView.findViewById(R.id.location_label);
        this.context = context;
        //set onclick listener
        itemView.setOnClickListener(this);
    }

    @Override
    public void onClick(View v) {
        Log.i("Click event: ", "My room has been clicked.");
        int pos = getAdapterPosition();
        Intent intent;
        ParseObject room = getCurrentList().get(pos);

        //create the ParseObject proxy
        ParseProxyObject roomProxy = new ParseProxyObject(room);
        Toast.makeText(context, room.getString("roomSuburb"), Toast.LENGTH_LONG).show();
        //fork to corresponding activity
        if(mSection != null) {
            Log.i("mSection text: ", "mSection text is: " + mSection);
            if (mSection.equals("My Rooms")) {
                //start my rooms detail activity
                Log.i("My room: ", "Room selected " + roomProxy.getObjectId());
                intent = new Intent(context, MyRoomDetailActivity.class);
                //add the room to the intent
                intent.putExtra("currentSelectedRoomObject", room);
                Log.i("Selected room", "Put Extra, " + room);
                intent.putExtra("roomObject", roomProxy);
                context.startActivity(intent);
            }
        }else {
            Log.i("My room:", "RoomDetailActivity loaded for MyRoomDetail Activity instead");
            intent = new Intent(context, RoomDetailActivity.class);
            //add the proxy to the intent
            intent.putExtra("roomObject", roomProxy);
            context.startActivity(intent);
        }

    }
}

@Override
public RoomViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
    //inflating the viewholder with the appropriate views
    View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.room_cardview, parent, false);

    return new RoomViewHolder(parent.getContext(), view);
}

@Override
public void onBindViewHolder(@NonNull RoomViewHolder holder, int position) {
    room = getItem(position);
    holder.mRoomLocation.setText(room.getString("roomSuburb"));
    holder.mRoomPrice.setText(Integer.toString(room.getInt("roomMonthlyRent")));
    holder.mInclusiveOrNot.setText(room.getString("roomRentInclusiveOfBills"));
    holder.mPropertyType.setText(room.getString("roomPropertyType"));
    holder.mNumOfBeds.setText(Integer.toString(room.getInt("roomBedrooms")));
    holder.mNumOfBaths.setText(Integer.toString(room.getInt("roomBathrooms")));

    //get the image
    //check if its roomImage or image1 set
    ParseFile imageFile;
    if (room.getParseFile("roomImage") != null){
        //
        imageFile = room.getParseFile("roomImage");
    }else {
        imageFile = room.getParseFile("roomImage1");
    }

    //if there is no image saved in Parse
    if(imageFile == null){
        //continue to load predefined default image
        int r = R.mipmap.ic_launcher;
        Glide.with(holder.mRoomImage.getContext()).load(r)
                .into(holder.mRoomImage);
    }else {
        Uri fileUri = Uri.parse(imageFile.getUrl());

        //image loader recommended by Google
        Glide.with(holder.mRoomImage.getContext()).load(fileUri.toString())
                .thumbnail(0.6f)
                .centerCrop()
                .crossFade()
                .into(holder.mRoomImage);
    }
}


public void addMoreRooms(List<ParseObject> newRooms){
    mRooms.addAll(newRooms);
    submitList((PagedList<ParseObject>) mRooms);
}

public void addAll(List<ParseObject> latestRooms) {
    mRooms.addAll(0, latestRooms);
    //mRooms.add(i, latestRooms);
    notifyDataSetChanged();
}
@Override
public Filter getFilter(){
  return new Filter() {
      @Override
      protected FilterResults performFiltering(CharSequence charSequence) {
          FilterResults results = new FilterResults();
          List<ParseObject> filteredList = null;
          if (charSequence == null || charSequence.length() == 0) {
              results.count = mRooms.size();
              results.values = mRooms;

              //results = mRooms.size();
          } else {
              filteredList = new ArrayList<>();
              charSequence = charSequence.toString().toLowerCase();
              for (ParseObject item : mRooms) {
                  String mSection = item.getObjectId().toLowerCase();
                  filteredList.add(item);
              }
          }

          results.count = filteredList.size();
          results.values = filteredList;

          return results;
      }

      @Override
      protected void publishResults(CharSequence charSequence, FilterResults results) {
          room = (ParseObject) results.values;
          notifyDataSetChanged();
      }
  };

}

【问题讨论】:

    标签: java android parsing


    【解决方案1】:

    制作您的适配器implements Filterable 并查看关于 SO 的THIS 主题,尤其是非常详细的答案。它是关于BaseAdapter,但负责过滤的部分对于所有适配器都是常见的。线索是在您的适配器中自定义覆盖 getFilter() 方法

    @Override
    public Filter getFilter() {
        return new Filter() {
            // implementation of your Filter
            ...
    

    并将querySearchView 传递给它

    @Override
    public boolean onSearchRequested() {
        String query - searchView.getText().toString();
        adapter.getFilter().filter(query);
        return true;
    }
    

    【讨论】:

    • 先生,我按照您说的更新了我的代码。但它不工作。我搜索时它没有显示列表。
    • 您的results.values 始终是= filterResults;。在publishResults 方法中,您正在更新mSectionmRooms 保持不变,除此之外还有ClassCastException,因为results.values 带有数组并且您正在转换为StringgetFilteredResults 也在做某事,但没有返回任何值(应该返回过滤数组恕我直言)
    • 先生,你能帮我写代码吗?我对这个程序感到困惑。我需要你的帮助。
    • 编辑您的问题并发布您的代码的最新版本(适配器和ActivityonCreate),以及ParseObject 的来源,我将使用一些解决方案编辑我的答案
    • 我已经发布了我的当前版本我的代码和 ParseObject 的来源。
    猜你喜欢
    • 2019-02-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-07-18
    • 1970-01-01
    相关资源
    最近更新 更多