java - Android 操作栏使用 customlitview 进行搜索

标签 java android android-listview searchbar android-search

我是 Android 开发新手。我使用 Arrayadopter 自定义 ListView ,我的所有数据都是从 sqlite 数据库获取的,并在此自定义 ListView 中显示如何在操作栏上实现搜索功能我尝试了许多其他代码,但它不起作用在这里,请告诉我是否有经验丰富的开发人员可以帮助我,我非常感谢他,请告诉我?

My custom list adopter:

    package bible.swordof.God;

    import android.app.Activity;
    import android.content.Context;
    import android.view.LayoutInflater;
    import android.view.View;
    import android.view.ViewGroup;
    import android.widget.ArrayAdapter;
    import android.widget.ImageView;
    import android.widget.TextView;

    import com.amulyakhare.textdrawable.TextDrawable;
    import com.amulyakhare.textdrawable.util.ColorGenerator;

    import java.util.ArrayList;
    import java.util.List;
    import java.util.Locale;

    public class ListViewAdapter extends ArrayAdapter<String> {
        private MainActivity activity;
        private List<String> friendList;
        private List<String> searchList;



        public ListViewAdapter(MainActivity context, int resource, List<String> objects) {
            super(context, resource, objects);
            this.activity = context;
            this.friendList = objects;
            this.searchList = new ArrayList<>();
            this.searchList.addAll(friendList);
        }



        @Override
        public int getCount() {
            return friendList.size();
        }

        @Override
        public String getItem(int position) {

            return friendList.get(position);


        }

        @Override
        public long getItemId(int position) {
            return position;
        }

        @Override
        public View getView(int position, View convertView, ViewGroup parent) {
            ViewHolder holder;
            LayoutInflater inflater = (LayoutInflater) activity.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
            // If holder not exist then locate all view from UI file.
            if (convertView == null) {
                // inflate UI from XML file
                convertView = inflater.inflate(R.layout.item_listview, parent, false);
                // get all UI view
                holder = new ViewHolder(convertView);
                // set tag for holder
                convertView.setTag(holder);
            } else {
                // if holder created, get tag from view
                holder = (ViewHolder) convertView.getTag();
            }

            holder.friendName.setText(getItem(position));



            //get first letter of each String item
            String firstLetter = String.valueOf(getItem(position).substring(0,1));


            ColorGenerator generator = ColorGenerator.MATERIAL; // or use DEFAULT
            // generate random color
            int color = generator.getColor(getItem(position));

            TextDrawable drawable = TextDrawable.builder()
                    .buildRound(firstLetter, color); // radius in px



            holder.imageView.setImageDrawable(drawable);



            return convertView;
        }

        public void filter(String charText) {
            charText = charText.toLowerCase(Locale.getDefault());
            friendList.clear();
            if (charText.length() == 0) {
                friendList.addAll(searchList);
            } else {
                for (String s : searchList) {
                    if (s.toLowerCase(Locale.getDefault()).contains(charText)) {
                        friendList.add(s);
                    }
                }
            }
            notifyDataSetChanged();
        }

        private class ViewHolder {
            private ImageView imageView;
            private TextView friendName;

            public ViewHolder(View v) {
                imageView = (ImageView) v.findViewById(R.id.image_view);
                friendName = (TextView) v.findViewById(R.id.text);
            }
        }

        }

My Mainactivity where i implement search bar:


package bible.swordof.God;

import android.app.Activity;
import android.content.Intent;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.speech.RecognizerIntent;
import android.support.design.widget.FloatingActionButton;
import android.support.design.widget.Snackbar;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentTransaction;
import android.support.v7.widget.SearchView;
import android.support.v7.widget.Toolbar;
import android.text.TextUtils;
import android.view.MenuInflater;
import android.view.View;
import android.support.design.widget.NavigationView;
import android.support.v4.view.GravityCompat;
import android.support.v4.widget.DrawerLayout;
import android.support.v7.app.ActionBarDrawerToggle;
import android.support.v7.app.AppCompatActivity;
import android.view.Menu;
import android.view.MenuItem;
import android.app.SearchManager;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.ListView;
import android.widget.SearchView.OnQueryTextListener;
import android.widget.SimpleCursorAdapter;
import android.widget.Toast;
import android.os.Bundle;
import android.support.v7.app.ActionBar;
import java.util.ArrayList;
import java.util.Locale;

public class MainActivity extends AppCompatActivity implements NavigationView.OnNavigationItemSelectedListener {
    private ListView listView;
    private ArrayList<String> stringArrayList;
    private ArrayAdapter<String> adapter;
    private DatabaseHelper mDBHelper=null;
    private SQLiteDatabase mDb=null;

//life is awesome

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        Toolbar toolbar=(Toolbar) findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);

        DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
        ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
                this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
        drawer.addDrawerListener(toggle);
        toggle.syncState();

        NavigationView navigationView = (NavigationView) findViewById(R.id.nav_view);
        navigationView.setNavigationItemSelectedListener(this);


        setData();
        listView =findViewById(R.id.list);
        adapter = new ListViewAdapter(MainActivity.this, R.layout.item_listview, stringArrayList);
        listView.setAdapter(adapter);

        listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
            @Override
            public void onItemClick(AdapterView<?> parent, View view, int position, long id) {

                 int booknumber=position+1;
                 String  bookname=stringArrayList.get(position);

                //Toast.makeText(MainActivity.this, ""+booknumber, Toast.LENGTH_SHORT).show();

                Intent intent=new Intent(MainActivity.this,Chapters.class);

                intent.putExtra("booknumber",booknumber);

                intent.putExtra("bookname",bookname);

                startActivity(intent);



            }
        });
    }



    @Override
    public void onBackPressed() {
        DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
        if (drawer.isDrawerOpen(GravityCompat.START)) {
            drawer.closeDrawer(GravityCompat.START);
        } else {
            super.onBackPressed();
        }
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {

        switch (item.getItemId()){
            case R.id.search_voice_btn:
                Intent intent = new Intent(RecognizerIntent.ACTION_RECOGNIZE_SPEECH);
                intent.putExtra(RecognizerIntent.EXTRA_LANGUAGE_MODEL, RecognizerIntent.LANGUAGE_MODEL_FREE_FORM);
                intent.putExtra(RecognizerIntent.EXTRA_LANGUAGE, Locale.getDefault());
                if (intent.resolveActivity(getPackageManager()) != null) {
                    startActivityForResult(intent, 10);
                } else {
                    Toast.makeText(this, "Your Device Don't Support Speech Input", Toast.LENGTH_SHORT).show();
                }




                break;
        }
        return super.onOptionsItemSelected(item);
    }
    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        super.onActivityResult(requestCode, resultCode, data);

        switch (requestCode) {
            case 10:
                if (resultCode == RESULT_OK && data != null) {

                    ArrayList<String> result = data.getStringArrayListExtra(RecognizerIntent.EXTRA_RESULTS);



                    Toast.makeText(this, ""+result.get(0), Toast.LENGTH_SHORT).show();



                }
                break;
        }
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        MenuInflater inflater=getMenuInflater();

    inflater.inflate(R.menu.main,menu);
    MenuItem menuItem=menu.findItem(R.id.action_search);




        SearchView searchView=(SearchView)menuItem.getActionView();



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



            }

            @Override
            public boolean onQueryTextChange(String newText) {
                if (TextUtils.isEmpty(newText)) {
                   adapter.getFilter().filter(newText);
                    listView.clearTextFilter();

                } else {
                    adapter.getFilter().filter(newText);
                }

                return true;


            }
        });

    return  true;
    }


    @SuppressWarnings("StatementWithEmptyBody")
    @Override
    public boolean onNavigationItemSelected(MenuItem item) {
        // Handle navigation view item clicks here.
        Fragment fragment;
        int id = item.getItemId();


        if (id == R.id.nav_camera) {





        } else if (id == R.id.favoruite)
        {
         Intent intent=new Intent(this,Favourite.class);

         startActivity(intent);
        }  else if (id == R.id.nav_manage) {

        } else if (id == R.id.nav_share) {

        } else if (id == R.id.nav_send) {

        }

        DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
        drawer.closeDrawer(GravityCompat.START);
        return true;
    }

    private void setData() {


        stringArrayList = new ArrayList<>();

        mDBHelper = new DatabaseHelper(this);
        mDb = mDBHelper.getReadableDatabase();

        Cursor cursor = mDb.rawQuery("select * from key_english", new String[]{});


        if(cursor!=null && cursor.getCount() > 0)
        {
            if (cursor.moveToFirst())
            {
                do {
                    stringArrayList.add(cursor.getString(1));
                } while (cursor.moveToNext());
            }
        }
            }


            }



My action search menu:
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto">

    <item
        android:id="@+id/action_search"
        android:title="@string/search"
        android:icon="@android:drawable/ic_menu_search"
        app:actionViewClass="android.support.v7.widget.SearchView"
        app:showAsAction="always" />

    <item
        android:id="@+id/search_voice_btn"
        android:icon="@drawable/ic_mic"
        app:showAsAction="always"
        android:title="Voice Search" />
</menu>

最佳答案

对于您的适配器,您创建了一个名为 filter 的公共(public)方法,它不是真正的 Filter 类。我建议两种不同的方法可以使发布的代码正常工作。

方法 1:在 Activity 中,将adapter.getFilter().filter(newText);更改为adapter.filter(newText);

方法2:由于您的数据是String列表,并且ArrayAdapter已经Filterable,因此保留adapter.getFilter().filter(newText); 并让适配器像这样简单:

public class ListViewAdapter extends ArrayAdapter {
private MainActivity activity;

public ListViewAdapter(MainActivity context, int resource, List<String> objects) {
    super(context, resource, objects);
    this.activity = context;
}

@Override
public View getView(int position, View convertView, ViewGroup parent) {
    ViewHolder holder;
    LayoutInflater inflater = (LayoutInflater) activity.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
    // If holder not exist then locate all view from UI file.
    if (convertView == null) {
        // inflate UI from XML file
        convertView = inflater.inflate(R.layout.item_listview, parent, false);
        // get all UI view
        holder = new ViewHolder(convertView);
        // set tag for holder
        convertView.setTag(holder);
    } else {
        // if holder created, get tag from view
        holder = (ViewHolder) convertView.getTag();
    }

    String item = (String)getItem(position);
    holder.friendName.setText(item);
    //get first letter of each String item
    String firstLetter = item.substring(0, 1);
    ColorGenerator generator = ColorGenerator.MATERIAL; // or use DEFAULT
    // generate random color
    int color = generator.getColor(item);
    TextDrawable drawable = TextDrawable.builder()
            .buildRound(firstLetter, color); // radius in px
    holder.imageView.setImageDrawable(drawable);
    return convertView;
}

private class ViewHolder {
    private ImageView imageView;
    private TextView friendName;

    public ViewHolder(View v) {
        imageView = (ImageView) v.findViewById(R.id.image_view);
        friendName = (TextView) v.findViewById(R.id.text);
    }
}

}

我在 ListView 上的博客还包含带有过滤器的示例:http://programandroidlistview.blogspot.com/希望有帮助!

关于java - Android 操作栏使用 customlitview 进行搜索,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56303333/

相关文章:

java.class.path 不带 Manifest.mf Class-Path 属性

android - 如何按日期和时间对 jsonarray 数据进行排序并放入 ListView 适配器

带有光标适配器滚动问题的android ListView

java - 使用 CustomAdapter 更改 ListView 的显示方式

java - 创建ApplicationContext后@Autowired Spring NullPointerException Null Beans

java - 如何同时管理多个版本的类?

java - 如何从日期报告参数获取年份-Birt Report

android - 更新后,android studio 出现错误

java - 如何在 Eclipse Android 开发中使用自定义 View ?

android - config.xml 文件中的 Ionic 2 调用、短信和邮件功能需要更改吗?