Bluetooth: Celular não localiza todos os dispositivos

Boa tarde pessoal

Estou escrevendo um programa J2ME que inicialmente irá localizar todos os dispositivos com bluetooth habilitados perto do celular que rodará esta aplicação.

Só que o resultado está muito inconstante: algumas vezes, ele encontra o meu pc com interface bluetooth, outras vezes um outro celular que está aqui comigo para testes.

Já fiz uns testes e o que está acontecendo é que o programa está fazendo a busca (agent.startInquiry(DiscoveryAgent.GIAC, this), e depois que encontra 1 dispositivo, encerra a pesquisa. Tentei fazer uma pesquisa pela aplicação bluetooth nativa do celular, só para testar, e ele encontra o PC e o outro telefone.

Tentei o mesmo código usado em uma aplicação J2SE e ele encontra tudo. Só neste telefone motorola ele faz a busca e pára. No nokia, ele faz a busca e nunca encontra nada.

O que estou fazendo de errado?

o Código:

Declaração da classe

public class ClienteME2 extends MIDlet implements DiscoveryListener{

Método principal

			LocalDevice localDevice = LocalDevice.getLocalDevice();
			//SHOW ALL INFORMATIONS 
			localName = localDevice.getFriendlyName();
			localAddress = localDevice.getBluetoothAddress();
			
			DiscoveryAgent agent = localDevice.getDiscoveryAgent();
			agent.startInquiry(DiscoveryAgent.GIAC, this);

			synchronized (this) 
			{
				try 
				{
					wait();
				} 
				catch (InterruptedException e) 
				{
					e.printStackTrace();
				}
			}//end of synchronized
		public void deviceDiscovered(RemoteDevice btDevice, DeviceClass cod) 
		{
			try
			{
				text += "\n" + btDevice.getFriendlyName(true);
				i++; //Com 2 dispositivos com BT ativado, no motorola sempre retorna 1 e no Nokia, 0 
			} 
			catch (IOException e) 
			{
				// TODO Auto-generated catch block
				e.printStackTrace();
			} 
	        
		}//End of deviceDiscovered method
	
		public void servicesDiscovered(int transID, ServiceRecord[] servRecord) {}//End of servicesDiscovered method
		public void serviceSearchCompleted(int transID, int respCode) {}//end of serviceSearchCompleted method
		
		public void inquiryCompleted(int discType) {
			synchronized (this) 
			{
				notify();
			}//end of synchronized (lock)
		}//end of inquiryCompleted method

[quote=FightSurf George Maia]Boa tarde pessoal

Estou escrevendo um programa J2ME que inicialmente irá localizar todos os dispositivos com bluetooth habilitados perto do celular que rodará esta aplicação.

Só que o resultado está muito inconstante: algumas vezes, ele encontra o meu pc com interface bluetooth, outras vezes um outro celular que está aqui comigo para testes.

Já fiz uns testes e o que está acontecendo é que o programa está fazendo a busca (agent.startInquiry(DiscoveryAgent.GIAC, this), e depois que encontra 1 dispositivo, encerra a pesquisa. Tentei fazer uma pesquisa pela aplicação bluetooth nativa do celular, só para testar, e ele encontra o PC e o outro telefone.

Tentei o mesmo código usado em uma aplicação J2SE e ele encontra tudo. Só neste telefone motorola ele faz a busca e pára. No nokia, ele faz a busca e nunca encontra nada.

O que estou fazendo de errado?

o Código:

Declaração da classe

public class ClienteME2 extends MIDlet implements DiscoveryListener{

Método principal

			LocalDevice localDevice = LocalDevice.getLocalDevice();
			//SHOW ALL INFORMATIONS 
			localName = localDevice.getFriendlyName();
			localAddress = localDevice.getBluetoothAddress();
			
			DiscoveryAgent agent = localDevice.getDiscoveryAgent();
			agent.startInquiry(DiscoveryAgent.GIAC, this);

			synchronized (this) 
			{
				try 
				{
					wait();
				} 
				catch (InterruptedException e) 
				{
					e.printStackTrace();
				}
			}//end of synchronized

[code]
public void deviceDiscovered(RemoteDevice btDevice, DeviceClass cod)
{
try
{
text += “\n” + btDevice.getFriendlyName(true);
i++; //Com 2 dispositivos com BT ativado, no motorola sempre retorna 1 e no Nokia, 0
}
catch (IOException e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}

	}//End of deviceDiscovered method

	public void servicesDiscovered(int transID, ServiceRecord[] servRecord) {}//End of servicesDiscovered method
	public void serviceSearchCompleted(int transID, int respCode) {}//end of serviceSearchCompleted method
	
	public void inquiryCompleted(int discType) {
		synchronized (this) 
		{
			notify();
		}//end of synchronized (lock)
	}//end of inquiryCompleted method

[/code][/quote]

Como em qualquer tipo de busca ou conexão, é recomendável fazer isto em uma thread separada (vários sites indicam isto). Eu mesmo não tenho este tipo de problema, e também não uso o seu tipo de abordagem. Seu trecho de código não deixa claro se está ou não fazendo uso de thread.

Chamo startInquiry em uma thread separada e tenho um Listener (BluetoothListener) que criei para ser notificado de dispositivos encontrados etc…enfim, foi decisão minha que fosse assim…

Outra dica é nunca realizar o startServiceSearch no deviceDiscovered pois isto pode atrapalhar a busca de outros dispositivos. Muitos aparelhos não suportam isto e existe uma propriedade que pode ser consultada via System.getProperty para saber se o aparelho suporta a busca de serviços intercalada com a de dispositivos.

Olá amigo

Fiz uma arrumação em meu código, e como você falou, coloquei a implementação toda dentro de uma thread. Criei uma classe extra implementando o DiscoveryListener e no final deu certo.

Estou colocando o código completo da minha classe aqui, para fins de pesquisa. Se alguém encontrar algum erro, redundância, ou sugerir melhoramento, por favor corrija-o e publique novamente neste post.

Este código foi escrito com base nos exemplos do Luis Henrique Albinati Junior.

Um forte abraço a todos e muito obrigado pela ajuda.

package br.com.fightsurf;//If you use, please change for your package

import java.io.IOException;
import java.util.Vector;

import javax.bluetooth.BluetoothStateException;
import javax.bluetooth.DeviceClass;
import javax.bluetooth.DiscoveryAgent;
import javax.bluetooth.DiscoveryListener;
import javax.bluetooth.LocalDevice;
import javax.bluetooth.RemoteDevice;
import javax.bluetooth.ServiceRecord;

import javax.microedition.lcdui.Display;
import javax.microedition.lcdui.TextBox;
import javax.microedition.midlet.MIDlet;
import javax.microedition.midlet.MIDletStateChangeException;

public class ClienteME2 extends MIDlet implements Runnable{
	
    private InquiryListener inq_listener;
    private String[] devicesFound;
	private String localName, localAddress;
	Display display;
	TextBox textbox;
	String text;
	
	//Constructor
	public ClienteME2() {
		Thread t = new Thread(this);
		t.start();
	}//end of constructor
	
	
	
	public void run()
	{
		try 
		{
			LocalDevice localDevice = LocalDevice.getLocalDevice();
			DiscoveryAgent agent = localDevice.getDiscoveryAgent();
			localDevice.setDiscoverable(DiscoveryAgent.GIAC);
			localName = localDevice.getFriendlyName();
			localAddress = localDevice.getBluetoothAddress();
    
            inq_listener = new InquiryListener();
            synchronized(inq_listener)	
            {
                agent.startInquiry(DiscoveryAgent.GIAC, inq_listener);
                try 
                {
                	inq_listener.wait(); 
                }  
                catch(InterruptedException e)
                {
                	e.printStackTrace();
                }
            }//end of synchronized

            //Count the number of devices
			int deviceCount = inq_listener.cached_devices.size();
			if(deviceCount > 0)
			{
				devicesFound = new String[deviceCount];
				for(int i = 0; i < deviceCount; i++)
				{
					try
					{
						RemoteDevice remoteDevice = (RemoteDevice)inq_listener.cached_devices.elementAt(i); 
						devicesFound[i] = i + 1 + ". " + remoteDevice.getBluetoothAddress() + " (" +
							remoteDevice.getFriendlyName(true) + ")";
					}//end of try
					catch(Exception e)
					{
						e.printStackTrace();
					}//end of catch()
	
				}//end of for(int i = 0; i < deviceCount; i++)
			}//end of if(deviceCount > 0)
			
			//Prepare the Text string for result final in Mobile phone's display 	
			text = new String();
			text = "";       
            
			for(int i = 0; i < deviceCount; i++)
				text += devicesFound[i] + "\n";

			text += "\n" + "Local Name: " + localName + "\nLocal Address: " + localAddress;
			display = Display.getDisplay(this);
			textbox = new TextBox("titulo", text, 1000,0);
			display.setCurrent(textbox);
			
		}//end of try 
		catch (BluetoothStateException e) 
		{
			e.printStackTrace();
		}//end of catch
	}//End of run method
	
	//ANOTHER METHODS FOR MIDLET APPLICATION: AFTER TO IMPLEMENT
	protected void destroyApp(boolean arg0) throws MIDletStateChangeException {}
	protected void pauseApp() {}
	protected void startApp() throws MIDletStateChangeException {}

}//end of class ClienteME2



/*************************
 * 
 * CLASS INQUIRY LISTENER
 *
 ************************/


class InquiryListener implements DiscoveryListener 
{
    public Vector cached_devices;
    
    //Constructor
    public InquiryListener() 
    {
        cached_devices = new Vector();
    }//end of constructor


    //STARTS WHEN SOME DEVICE IS DISCOVERED
    public void deviceDiscovered( RemoteDevice btDevice, DeviceClass cod )	
    {
        if( ! cached_devices.contains( btDevice ))	
        {
            cached_devices.addElement( btDevice );
            
        }//end of if
    }//end of deviceDiscovered method
    
    
    //STARTS WHEN INQUIRY IS COMPLETED
    public void inquiryCompleted( int discType )	
    {
        synchronized(this)
        {	
        	this.notify(); 
        }//end of synchronized
    }//end of inquiryCompleted method
    
    
    //SERVICES METHODS: AFTER TO IMPLEMENT
    public void servicesDiscovered( int transID, ServiceRecord[] servRecord )	{}
    public void serviceSearchCompleted( int transID, int respCode )	{}



}//end of class InquiryListener