首页 > 解决方案 > 我不能将上下文传递给适配器类

问题描述

我编写了一个应用程序,它将发现蓝牙设备并将它们显示在位于片段中的 ListView 中。这是我在片段中的代码:

class ScanFragment: Fragment() {

val device_list = ArrayList<DataSource>()
val paired_device_list = ArrayList<DataSource>()
val btAdapter = BluetoothAdapter.getDefaultAdapter()
var rvAdapter: RVAdapter? = null

override fun onCreateView(
    inflater: LayoutInflater,
    container: ViewGroup?,
    savedInstanceState: Bundle?
): View? {
    val view: View? = inflater.inflate(R.layout.scan_fragment, container, false)

    val lvDevices = view?.findViewById<ListView>(R.id.lvDevices)

    val device1 = DataSource("Test_Xiaomi", "Test_MAC_Address")
    val device2 = DataSource("Test_Huawei", "Test_MAC_Adress")
    device_list.add(device1)
    device_list.add(device2)
    lvDevices?.adapter = RVAdapter(activity, R.layout.rv_items, device_list)
    rvAdapter?.notifyDataSetChanged()
    Log.d("TAG", "Device = $device_list")

    val filter = IntentFilter(BluetoothDevice.ACTION_FOUND)
    activity?.registerReceiver(receiver, filter)

    return view
}

override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
    super.onViewCreated(view, savedInstanceState)

    val paired_devices: Set<BluetoothDevice> = btAdapter.bondedDevices
    for(device: BluetoothDevice in paired_devices) {
        val ok_paired_devices = DataSource(device.name.toString(), device.address.toString())
        paired_device_list.add(ok_paired_devices)
    }
}

val receiver = object: BroadcastReceiver() {
    override fun onReceive(context: Context?, intent: Intent?) {
        val action: String? = intent?.action
        if(BluetoothDevice.ACTION_FOUND == action) {
            val device: BluetoothDevice? = intent.getParcelableExtra<BluetoothDevice>(BluetoothDevice.EXTRA_DEVICE)
            val newDevice = DataSource(device?.name.toString(), device?.address.toString())
            device_list.add(newDevice)
            val lvDevice = view?.findViewById<ListView>(R.id.lvDevices)
            lvDevice?.adapter = RVAdapter(activity, R.layout.rv_items, device_list)
            //Log.d("TAG", "Device = $device_list")
        }
    }
}

override fun onDestroyView() {
    super.onDestroyView()
    activity?.unregisterReceiver(receiver)
}

这是我的适配器:

class RVAdapter(context: Context, var res: Int, var list: ArrayList<DataSource>): ArrayAdapter<DataSource>(context, res, list) {

    override fun getView(position: Int, convertView: View?, parent: ViewGroup): View {
         //super.getView(position, convertView, parent)

        val inflater = LayoutInflater.from(context)
        val row = inflater.inflate(res, parent, false)

        val tvDeviceName = convertView?.findViewById<TextView>(R.id.tvDeviceName)
        val tvDeviceMAC = convertView?.findViewById<TextView>(R.id.tvDeviceMAC)

        var item = list[position]

        tvDeviceName?.text =  item.device_name
        tvDeviceMAC?.text = item.device_mac

        return row
    }

我只是不能将上下文从片段传递给我的适配器。我尝试传递“活动”或“上下文”或“MainActivity()”,但 ListView 根本不显示任何内容。如果我将“MainActivity()”准确地传递给适配器,那么我会在行中收到错误消息“系统服务在 onCreate() 之前对活动不可用”

lvDevices?.adapter = RVAdapter(activity, R.layout.rv_items, device_list).

并在线

class RVAdapter(context: Context, var res: Int, var list: ArrayList<DataSource>): ArrayAdapter<DataSource>(context, res, list)

如果我尝试传递“活动”,那么它只会以红色突出显示。当我改用 recyclerView 时,一切都很好。但我不想使用 RecyclerView,因为我多次尝试以不同的方式实现 onItemClick,但对我没有任何作用,因为我无法在 onReceive 方法中传递上下文。

标签: androidlistviewkotlinbluetoothfragment

解决方案


问题是activity属性返回可空类型,但适配器需要不可空类型。如果您需要片段中的上下文,请调用requireContext()

RVAdapter(requireContext(), R.layout.rv_items, device_list)

推荐阅读