01-自定义控件+ListView+RecyclerView

1.自定义控件

1:编写控件xml。
2:编写Kotlin类继承相关Layout。
3:在需要的地方通过类的全名(com.my.uicustomviews.TitleLayout)引入。
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="horizontal" android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:background="@drawable/title_bg">

    <Button
        android:id="@+id/back"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:background="@drawable/edit_bg"
        android:layout_gravity="center"
        android:layout_margin="5dp"
        android:textColor="#fff"
        android:text="back"/>

    <TextView
        android:id="@+id/text"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_weight="1"
        android:gravity="center"
        android:layout_gravity="center"
        android:textColor="#fff"
        android:textSize="24sp"
        android:text="Title Text"/>

    <Button
        android:id="@+id/edit"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:background="@drawable/edit_bg"
        android:layout_gravity="center"
        android:layout_margin="5dp"
        android:textColor="#fff"
        android:text="edit"/>
</LinearLayout>

<com.my.uicustomviews.TitleLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>
class TitleLayout(context : Context,attr : AttributeSet) :
    LinearLayout(context , attr) {

    init {
        LayoutInflater.from(context).inflate(R.layout.title,this)

        back.setOnClickListener {
            val a = context as Activity
            a.finish()
        }

        edit.setOnClickListener {
            Toast.makeText(context,"You click",Toast.LENGTH_SHORT).show()
        }
    }
}

2.初级ListView

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <ListView
        android:id="@+id/listView"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>

</LinearLayout>
class MainActivity : AppCompatActivity() {

    private val list = listOf("Apple","Banana","Orange","Watermelon",
        "Pear","Grape","Pineapple","Strawberry","Cherry",
        "Mango")

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        //android.R.layout.simple_expandable_list_item_1,Android内置布局,只包含一个TextView
        val adapter =  ArrayAdapter<String>(this,android.R.layout.simple_expandable_list_item_1,list)
        listView.adapter = adapter
    }
}

3.高级ListView

1:创建单个item的布局,主布局中引入ListView。
2:创建实体类,封装数据。
3:创建Adapter适配器,填充item布局。
4:ListView引用Adapte对象。
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="horizontal" android:layout_width="match_parent"
    android:layout_height="60dp">

    <ImageView
        android:id="@+id/image"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="center_vertical"/>

    <TextView
        android:id="@+id/name"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginStart="5dp"
        android:layout_gravity="center_vertical"/>
</LinearLayout>

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <ListView
        android:id="@+id/listView"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>

</LinearLayout>
class Fruit(val name : String , val imageId : Int)

class FruitAdapter(activity : Activity , resourceId : Int ,
                   data : List<Fruit>) : ArrayAdapter<Fruit>(activity,resourceId,data) {

    override fun getView(position: Int, convertView: View?, parent: ViewGroup): View {
        val view = LayoutInflater.from(context).inflate(R.layout.fruit_item,
            parent,false)

        val fruit = getItem(position)

        val imageView : ImageView = view.findViewById(R.id.image)
        val textView : TextView = view.findViewById(R.id.name)

        if (fruit != null){
            imageView.setImageResource(fruit.imageId)
            textView.text = fruit.name
        }
        return view
    }
}

class MainActivity : AppCompatActivity() {

    private val data = ArrayList<Fruit>()

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        initData()
        val fruitAdapter = FruitAdapter(this,R.layout.fruit_item,data)
        listView.adapter = fruitAdapter
    }

    private fun initData(){
        //repeat(2),重复执行两次代码
        repeat(2) {
            data.add(Fruit("Apple",R.drawable.apple_pic))
            data.add(Fruit("Banana",R.drawable.banana_pic))
            data.add(Fruit("Orange",R.drawable.orange_pic))
            data.add(Fruit("Watermelon",R.drawable.watermelon_pic))
            data.add(Fruit("Pear",R.drawable.pear_pic))
            data.add(Fruit("Grape",R.drawable.grape_pic))
            data.add(Fruit("Pineapple",R.drawable.pineapple_pic))
            data.add(Fruit("Strawberry",R.drawable.strawberry_pic))
            data.add(Fruit("Cherry",R.drawable.cherry_pic))
            data.add(Fruit("Mango",R.drawable.mango_pic))
        }
    }
}

4.ListView优化

class FruitAdapter(activity : Activity , resourceId : Int ,
                   data : List<Fruit>) : ArrayAdapter<Fruit>(activity,resourceId,data) {

    /**
     * 使用内部类缓存ImageView、TextView对象,使得每次不需要调用findViewById()
     */
    inner class ViewHolder(val imageView : ImageView ,
                           val textView : TextView)

    override fun getView(position: Int, convertView: View?, parent: ViewGroup): View {
        val view : View
        val viewHolder : ViewHolder
        if (convertView == null){
            view = LayoutInflater.from(context).inflate(R.layout.fruit_item,
                parent,false)

            //将数据缓存到ViewHolder中
            val imageView : ImageView = view.findViewById(R.id.image)
            val textView : TextView = view.findViewById(R.id.name)
            viewHolder = ViewHolder(imageView,textView)
            view.tag = viewHolder
        }else {
            view = convertView
            //从缓存中取出数据
            viewHolder = view.tag as ViewHolder
        }

        val fruit = getItem(position)
        
        if (fruit != null){
            viewHolder.imageView.setImageResource(fruit.imageId)
            viewHolder.textView.text = fruit.name
        }
        return view
    }
}

5.ListView的点击事件

listView.setOnItemClickListener { parent, view, position, id ->
    val fruit = data[position]
    Toast.makeText(this,"ok ${fruit.name}",Toast.LENGTH_SHORT).show()
}

//无用参数可以使用_代替
listView.setOnItemClickListener { _, _, position, _ ->
	val fruit = data[position]
	Toast.makeText(this,"ok ${fruit.name}",Toast.LENGTH_SHORT).show()
}

6.RecyclerView

1:和ListView的使用流程相同,但是需要引入implementation 'androidx.recyclerview:recyclerview:1.1.0'
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="horizontal" android:layout_width="match_parent"
    android:layout_height="60dp">

    <ImageView
        android:id="@+id/image"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="center_vertical"/>

    <TextView
        android:id="@+id/name"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginStart="5dp"
        android:layout_gravity="center_vertical"/>
</LinearLayout>

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <androidx.recyclerview.widget.RecyclerView
        android:id="@+id/recyclerView"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>

</LinearLayout>
class Fruit(val name : String , val imageId : Int)

class FruitAdapter(private val fruits : List<Fruit>) : RecyclerView.Adapter<FruitAdapter.ViewHolder>() {

    inner class ViewHolder(view : View) : RecyclerView.ViewHolder(view){
        val imageView : ImageView = view.findViewById(R.id.image)
        val textView : TextView = view.findViewById(R.id.name)
    }

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
        val view = LayoutInflater.from(parent.context).inflate(R.layout.fruit_item,parent,false)
        return ViewHolder(view)
    }

    override fun getItemCount(): Int = fruits.size

    override fun onBindViewHolder(holder: ViewHolder, position: Int) {
        val fruit = fruits[position]
        holder.imageView.setImageResource(fruit.imageId)
        holder.textView.text = fruit.name
    }

}

class MainActivity : AppCompatActivity() {

    private val data = ArrayList<Fruit>()

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        initFruit()
        val layoutManager = LinearLayoutManager(this)
        val adapter = FruitAdapter(data)
        recyclerView.layoutManager = layoutManager
        recyclerView.adapter = adapter
    }

    private fun initFruit(){
        //repeat(2),重复执行两次代码
        repeat(2) {
            data.add(Fruit("Apple",R.drawable.apple_pic))
            data.add(Fruit("Banana",R.drawable.banana_pic))
            data.add(Fruit("Orange",R.drawable.orange_pic))
            data.add(Fruit("Watermelon",R.drawable.watermelon_pic))
            data.add(Fruit("Pear",R.drawable.pear_pic))
            data.add(Fruit("Grape",R.drawable.grape_pic))
            data.add(Fruit("Pineapple",R.drawable.pineapple_pic))
            data.add(Fruit("Strawberry",R.drawable.strawberry_pic))
            data.add(Fruit("Cherry",R.drawable.cherry_pic))
            data.add(Fruit("Mango",R.drawable.mango_pic))
        }
    }
}

7.横向RecyclerView

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    setContentView(R.layout.activity_main)

    initFruit()
    val layoutManager = LinearLayoutManager(this)
    //横向RecyclerView
    layoutManager.orientation = LinearLayoutManager.HORIZONTAL
    val adapter = FruitAdapter(data)
    recyclerView.layoutManager = layoutManager
    recyclerView.adapter = adapter
}

8.瀑布流RecyclerView

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    setContentView(R.layout.activity_main)

    initFruit()
    //瀑布流式RecyclerView,3表示有三列
    //StaggeredGridLayoutManager.VERTICAL表示布局纵向排列
    val layoutManager = StaggeredGridLayoutManager(3,StaggeredGridLayoutManager.VERTICAL)
    layoutManager.orientation = LinearLayoutManager.HORIZONTAL


    val adapter = FruitAdapter(data)
    recyclerView.layoutManager = layoutManager
    recyclerView.adapter = adapter
}

9.RecyclerView的点击事件

class FruitAdapter(private val fruits : List<Fruit>) : RecyclerView.Adapter<FruitAdapter.ViewHolder>() {

    inner class ViewHolder(view : View) : RecyclerView.ViewHolder(view){
        val imageView : ImageView = view.findViewById(R.id.image)
        val textView : TextView = view.findViewById(R.id.name)
    }

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
        val view = LayoutInflater.from(parent.context).inflate(R.layout.fruit_item,parent,false)
        val viewHolder = ViewHolder(view)
        //通过ViewHolder为子项绑定点击事件
        viewHolder.imageView.setOnClickListener {
            val position = viewHolder.adapterPosition
            val fruit = fruits[position]
            Toast.makeText(parent.context,"Image You click ${fruit.name}",Toast.LENGTH_SHORT).show()
        }

        //通过ViewHolder为每一项绑定点击事件
        viewHolder.itemView.setOnClickListener {
            val position = viewHolder.adapterPosition
            val fruit = fruits[position]
            Toast.makeText(parent.context,"Item You click ${fruit.name}",Toast.LENGTH_SHORT).show()
        }
        return viewHolder
    }

    override fun getItemCount(): Int = fruits.size

    override fun onBindViewHolder(holder: ViewHolder, position: Int) {
        val fruit = fruits[position]
        holder.imageView.setImageResource(fruit.imageId)
        holder.textView.text = fruit.name
    }

}
©️2020 CSDN 皮肤主题: 游动-白 设计师:上身试试 返回首页