2013-01-23 55 views
0

我有一个应用程序,它在按钮(切换按钮)上按下扫描并在自定义列表视图中显示发现的蓝牙设备,再次按下相同的按钮时扫描停止。Listview显示重复扫描的蓝牙设备的重复条目

现在问题出现,当我再次按下按钮(第二次)开始扫描时,同一设备显示两次。停止并开始扫描(第三次)后,同一设备显示三次。所发现的设备从未与我的android手机配对。

还有一个类似的question,但答案并没有帮助我。请让我知道我出错的地方。

下面是代码

 btOnOff.setOnClickListener(new OnClickListener() { 
     @Override 
     public void onClick(View v) { 
      // TODO Auto-generated method stub 
      if(btOnOff.isChecked()){ 

       btAdapter.startDiscovery(); 
       setProgressBarIndeterminateVisibility(true); 

        bcReceiver = new BroadcastReceiver() { 
         @Override 
         public void onReceive(Context context, Intent intent) { 
          // TODO Auto-generated method stub 
          String action = intent.getAction(); 
          if(BluetoothDevice.ACTION_FOUND.equals(action)){ 
           BluetoothDevice device = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE); 

           deviceName = device.getName(); 
           currentDateTime = DateFormat.getDateTimeInstance().format(new Date()); 

           Custom data = new Custom(deviceName, currentDateTime); 
           fetch.add(data); 

           lv.setAdapter(cAdapter); 

          }else if(btAdapter.ACTION_DISCOVERY_FINISHED.equals(action)){ 
           btAdapter.startDiscovery(); 
          } 
         } 
        }; 

        IntentFilter filter = new IntentFilter(BluetoothDevice.ACTION_FOUND); 
        registerReceiver(bcReceiver, filter); 
      } else { 
       btAdapter.cancelDiscovery(); 
      } 
     } 

    }); 

我还有两节课这确实列表视图的定制,莫不是什么,以避免重复的条目。下面是第一类文件的代码

public class CustomAdapter extends ArrayAdapter<Custom>{ 

private ArrayList<Custom> entries; 
private Activity activity; 

public CustomAdapter(Activity a, int textViewResourceId, ArrayList<Custom> entries) { 
    super(a, textViewResourceId, entries); 
    // TODO Auto-generated constructor stub 
    this.entries = entries; 
    this.activity = a; 
} 

public static class ViewHolder{ 
    public TextView tv1; 
    public TextView tv2; 
} 

@Override 
public View getView(int position, View convertView, ViewGroup parent){ 
    View v = convertView; 
    ViewHolder holder; 
    if(v == null){ 
     LayoutInflater vi = (LayoutInflater)activity.getSystemService(Context.LAYOUT_INFLATER_SERVICE); 
     v = vi.inflate(R.layout.show_devices, null); 
     holder = new ViewHolder(); 
     holder.tv1 = (TextView) v.findViewById(R.id.tv1); 
     holder.tv2 = (TextView) v.findViewById(R.id.tv2); 

     v.setTag(holder); 
    }else{ 
     holder = (ViewHolder)v.getTag(); 
    } 

    final Custom custom = entries.get(position); 
    if(custom != null){ 
     holder.tv1.setText(custom.getFirst()); 
     holder.tv2.setText(custom.getSecond()); 
    } 
    return v; 
} 

}

第二类文件

public class Custom { 
private String text1; 
private String text2; 

public Custom(String string1, String string2){ 
    this.text1 = string1; 
    this.text2 = string2; 
} 

public String getFirst(){ 
    return text1; 
} 

public void setFirst(String text1){ 
    this.text1 = text1; 
} 

public String getSecond(){ 
    return text2; 
} 

public void setSecond(String text2){ 
    this.text2 = text2; 
} 
} 

回答

0

自定义列表视图与上面使用的逻辑类型创建冗余和重复的条目被创建。因此,我们可以使用simple_list_item_1来使用ArrayAdapter,而不是使用另外两个类来编写自定义列表视图。

在Button onclick事件中,ArrayAdapter对象将清除重复条目,而simple_list_item_1将提供与自定义列表视图类似的两行listview。

简单的实现表明here

2

当你开始重新扫描,您的列表中明确的项目“取” ..基本上什么你做的是,每次你扫描,你添加蓝牙搜索设备到以前的列表..

+0

在我开始发现设备之前,我使用cAdapter.clear()清除了列表。扫描开始时,列表被清除,但稍后在同一台设备上列出旧时间戳。 – User210282

+0

即使使用fetch.clear()也不会清除列表。 – User210282

+0

所以你想说重新扫描之前清单不清除?它包含以前结果的元素? –

0

如果无法使用默认的列表视图适配器,就像你要显示在dialogfragment或类似的东西的设备,这是我不那么优雅的解决方案,以避免重复当它们被重新扫描时出现相同的设备:

private final BroadcastReceiver mReceiver = new BroadcastReceiver() { 
    public void onReceive(Context context, Intent intent) { 
     String action = intent.getAction(); 
     // When discovery finds a device 

     if (BluetoothDevice.ACTION_FOUND.equals(action)) { 
      // Get the BluetoothDevice object from the Intent 
      device = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE); 
      if(count ==0){ 
       prev_device = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE); 
       mArrayAdapter.add(device.getName() + "\n" + device.getAddress()); 
       mArrayAdapter.notifyDataSetChanged(); 
      } 
      Log.d("BLUETOOTH","count = "+count); 
      if(!device.getAddress().contains(prev_device.getAddress())){ 
       Log.d("BLUETOOTH","NOT A MATCH - ADD TO LIST"); 
      // Add the name and address to an array adapter to show in a ListView 
       mArrayAdapter.add(device.getName() + "\n" + device.getAddress()); 
       mArrayAdapter.notifyDataSetChanged(); 
      } 

      prev_device = device; 

      if(count ==0){ 
       showDevices(); //Simply displays a dialogFragment with listview of devices 
      } 
      count++; 
     } 
    } 
}; 

基本上你检查设备是否先前被扫描过。但是,这只适用于只有一个设备的情况下(对于我的应用程序),但如果您需要适应多个设备,则需要存储以前的所有地址,并将其解析为只查看并只显示新设备。

+0

感谢您的帮助,我的问题已解决与我张贴的答案。 – User210282

0

我有同样的问题。只需将接收器放在onclick之外,在oncreate下。 由于它处于onclick状态,因此接收器将被初始化两次,因此会出现重复设备。

在onclick取下接收器,并把它下的OnCreate

0

你需要明确的是,你在使用的适配器列表。像这样 - >

private fun setAdapterToListView() { 

     devicesNameAddressList.clear() 
     for (i in 0 until devicesName.size) { 
      val list = HashMap<String, String>() 
      list.put("line1", devicesName[i]) 
      list.put("line2", devicesAddress[i]) 
      devicesNameAddressList.add(list) 
     } 

     val simpleAdapter = SimpleAdapter(this, devicesNameAddressList, R.layout.devices_listview_texttype, 
       arrayOf("line1", "line2"), intArrayOf(R.id.line_a, R.id.line_b)) 
     BluetoothDevicesListID.adapter = simpleAdapter 
    } 
0

对于蓝牙设备有MAC地址,您可以匹配MAC地址,并从列表中删除重复的设备。