Bluetooth経由で受信した動的な値をプロットするアプリを構築しています。androidは初めてなので、android開発者ガイドのチュートリアルを使用しましたが、Thread.start()メソッドにアクセスしようとするとアプリケーションがクラッシュします。これがコードです。エミュレータがBluetoothをサポートしていないため、LogCatを投稿できませんでした。これがコードです。 MainActivity.java
package com.example.enose.sensor;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.LinkedList;
import java.util.Set;
import java.util.UUID;
import android.app.Activity;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothSocket;
import android.content.Context;
import android.graphics.Color;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.os.MessageQueue;
import android.widget.TextView;
import android.widget.Toast;
import com.androidplot.xy.BoundaryMode;
import com.androidplot.xy.LineAndPointFormatter;
import com.androidplot.xy.LineAndPointRenderer;
import com.androidplot.xy.SimpleXYSeries;
import com.androidplot.xy.XYPlot;
public class MainActivity extends Activity {
@Override
protected void onStop() {
// TODO Auto-generated method stub
super.onStop();
}
private static final int HISTORY_SIZE = 30;
public static final int MESSAGE_READ = 0;
private XYPlot aprHistoryPlot = null;
private SimpleXYSeries alcohol=null;
private SimpleXYSeries lpg=null;
private SimpleXYSeries methane=null;
private SimpleXYSeries quality=null;
private LinkedList<Number> alcoholHistory;
private LinkedList<Number> lpgHistory;
private BluetoothAdapter mBluetoothAdapter;
//private UUID uid;
//Thread to initiate connection
private class ConnectThread extends Thread {
private final BluetoothSocket mmSocket;
private final BluetoothDevice mmDevice;
public ConnectThread(BluetoothDevice device) {
// Use a temporary object that is later assigned to mmSocket,
// because mmSocket is final
BluetoothSocket tmp = null;
mmDevice = device;
// Get a BluetoothSocket to connect with the given BluetoothDevice
try {
tmp = device.createRfcommSocketToServiceRecord(UUID.fromString("0000110100001000800000805F9B34FB"));
} catch (IOException e) { }
mmSocket = tmp;
}
public void run() {
// Cancel discovery because it will slow down the connection
mBluetoothAdapter.cancelDiscovery();
try {
// Connect the device through the socket. This will block
// until it succeeds or throws an exception
mmSocket.connect();
} catch (IOException connectException) {
// Unable to connect; close the socket and get out
try {
mmSocket.close();
} catch (IOException closeException) { }
return;
}
// Do work to manage the connection (in a separate thread)
//manageConnectedSocket(mmSocket);
}
public void manageConnectedSocket(BluetoothSocket socket)
{
ConnectedThread data=new ConnectedThread(socket);
data.start();
}
/** Will cancel an in-progress connection, and close the socket */
public void cancel() {
try {
mmSocket.close();
} catch (IOException e) { }
}
}
public class ConnectedThread extends Thread {
private final BluetoothSocket mmSocket;
private final InputStream mmInStream;
private final OutputStream mmOutStream;
public ConnectedThread(BluetoothSocket socket) {
mmSocket = socket;
InputStream tmpIn = null;
OutputStream tmpOut = null;
// Get the input and output streams, using temp objects because
// member streams are final
try {
tmpIn = socket.getInputStream();
tmpOut = socket.getOutputStream();
} catch (IOException e) { }
mmInStream = tmpIn;
mmOutStream = tmpOut;
}
public void run() {
byte[] buffer = new byte[1024]; // buffer store for the stream
int bytes; // bytes returned from read()
// Keep listening to the InputStream until an exception occurs
while (true) {
try {
// Read from the InputStream
bytes = mmInStream.read(buffer);
// Send the obtained bytes to the UI activity
// h.obtainMessage(MESSAGE_READ,bytes,-1,buffer)
// .sendToTarget();
} catch (IOException e) {
break;
}
}
}
/* Call this from the main activity to send data to the remote device */
public void write(byte[] bytes) {
try {
mmOutStream.write(bytes);
} catch (IOException e) { }
}
/* Call this from the main activity to shutdown the connection */
public void cancel() {
try {
mmSocket.close();
} catch (IOException e) { }
}
}
private LinkedList<Number> methaneHistory;
{
alcoholHistory = new LinkedList<Number>();
lpgHistory = new LinkedList<Number>();
methaneHistory = new LinkedList<Number>();
alcohol = new SimpleXYSeries("Alcohol");
lpg = new SimpleXYSeries("LPG");
methane = new SimpleXYSeries("Methane");
quality = new SimpleXYSeries("Air Quality");
}
private class MyHandler extends Handler
{
@Override
public void handleMessage(Message msg) {
// TODO Auto-generated method stub
super.handleMessage(msg);
int val=msg.arg1;
byte[] d=(byte[]) msg.obj;
Double s1;
s1=Double.longBitsToDouble(val);
alcoholHistory.addLast(s1);
if(alcoholHistory.size()>30)
alcoholHistory.removeFirst();
alcohol.setModel(alcoholHistory,SimpleXYSeries.ArrayFormat.Y_VALS_ONLY);
aprHistoryPlot.redraw();
}
}
//MyHandler h;
private BluetoothDevice selDevice;
private Context context;
private BluetoothSocket tmp;
private ConnectThread connect;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Handler h=new Handler();
context=this;
setContentView(R.layout.activity_main);
aprHistoryPlot = (XYPlot) findViewById(R.id.aprHistoryPlot);
alcoholHistory.addFirst(2);
lpgHistory.addFirst(3);
methaneHistory.addFirst(4);
alcoholHistory.addFirst(3);
lpgHistory.addFirst(2);
methaneHistory.addFirst(1);
alcohol.setModel(alcoholHistory, SimpleXYSeries.ArrayFormat.Y_VALS_ONLY);
lpg.setModel(lpgHistory, SimpleXYSeries.ArrayFormat.Y_VALS_ONLY);
methane.setModel(methaneHistory, SimpleXYSeries.ArrayFormat.Y_VALS_ONLY);
aprHistoryPlot.setRangeBoundaries(0, 5,BoundaryMode.FIXED);
aprHistoryPlot.setDomainBoundaries(0, 30, BoundaryMode.FIXED);
aprHistoryPlot.addSeries(alcohol, LineAndPointRenderer.class, new LineAndPointFormatter(Color.rgb(0, 100, 200), Color.BLACK,null));
aprHistoryPlot.addSeries(lpg, LineAndPointRenderer.class, new LineAndPointFormatter(Color.rgb(100, 200, 100), Color.BLACK,null));
aprHistoryPlot.addSeries(methane, LineAndPointRenderer.class, new LineAndPointFormatter(Color.rgb(200, 100, 100), Color.BLACK,null));
aprHistoryPlot.setDomainStepValue(1);
aprHistoryPlot.setTicksPerRangeLabel(3);
aprHistoryPlot.setDomainLabel("time");
aprHistoryPlot.getDomainLabelWidget().pack();
aprHistoryPlot.setRangeLabel("level");
aprHistoryPlot.getRangeLabelWidget().pack();
aprHistoryPlot.disableAllMarkup();
mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter();
if (mBluetoothAdapter == null) {
// Device does not support Bluetooth
Toast.makeText(context, "Not supported", Toast.LENGTH_LONG).show();
}
else{
//Toast.makeText(context, "test1", Toast.LENGTH_SHORT).show();
if (!mBluetoothAdapter.isEnabled()) {
mBluetoothAdapter.enable();
// Intent enableBtIntent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
// startActivityForResult(enableBtIntent, REQUEST_ENABLE_BT);
}
Toast.makeText(context, "test2", Toast.LENGTH_SHORT).show();
Set<BluetoothDevice> devices=mBluetoothAdapter.getBondedDevices();
boolean isDeviceSet=false;
if(devices==null)
{
Toast.makeText(context, "No paired devices", Toast.LENGTH_LONG).show();
}
else
{
//Toast.makeText(context, "test3", Toast.LENGTH_SHORT).show();
//BluetoothDevice dev=mBluetoothAdapter.getRemoteDevice("006645ffly477");
for (BluetoothDevice device : devices) {
// Add the name and address to an array adapter to show in a ListView
//mArrayAdapter.add(device.getName() + "\n" + device.getAddress());
selDevice=device;
isDeviceSet=true;
//TextView tv=(TextView) findViewById(R.id.txtlist);
//tv.setText("Bluetooth device "+selDevice.getName()+" selected");
break;
}
Message msg=h.obtainMessage();
//uid=new UUID(7659464,976328762);
//Toast.makeText(context, "test4", Toast.LENGTH_SHORT ).show();
//connect=new ConnectThread(dev);
//connect.run();
//dev=mBluetoothAdapter.getRemoteDevice("006645ffly477");
//if(dev!=null)
//Toast.makeText(context, "device null", Toast.LENGTH_SHORT).show();
//else
//connect=new ConnectThread(selDevice);
// connect.run();
}
}
}
}
AndroidManifest.xml
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.enose.sensor"
android:versionCode="1"
android:versionName="1.0" >
<uses-sdk
android:minSdkVersion="5"
android:targetSdkVersion="10" />
<uses-permission android:name="android.permission.BLUETOOTH" />
<application
android:icon="@drawable/ic_launcher"
android:label="@string/app_name" >
<activity
android:name=".MainActivity"
android:label="@string/title_activity_main" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
</manifest>
activity_main.xml
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<com.androidplot.xy.XYPlot
android:id="@+id/aprHistoryPlot"
android:layout_width="fill_parent"
android:layout_height="200dp"
android:layout_marginTop="10px"
android:layout_marginLeft="10px"
android:layout_marginRight="10px"
title="eNose Readings"/>
<TextView
android:id="@+id/txtlist"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"/>
</RelativeLayout>
Logcat
10-04 16:09:01.508: E/InputDispatcher(62): channel '4074d648 com.example.enose.sensor/com.example.enose.sensor.MainActivity (server)' ~ Consumer closed input channel or an error occurred. events=0x8
10-04 16:09:01.508: E/InputDispatcher(62): channel '4074d648 com.example.enose.sensor/com.example.enose.sensor.MainActivity (server)' ~ Channel is unrecoverably broken and will be disposed!
10-04 16:12:09.808: E/InputDispatcher(62): channel '405ecbb8 com.example.enose.sensor/com.example.enose.sensor.MainActivity (server)' ~ Consumer closed input channel or an error occurred. events=0x8
10-04 16:12:09.808: E/InputDispatcher(62): channel '405ecbb8 com.example.enose.sensor/com.example.enose.sensor.MainActivity (server)' ~ Channel is unrecoverably broken and will be disposed!
10-04 21:11:42.588: E/InputDispatcher(62): channel '405a9a88 com.example.enose.sensor/com.example.enose.sensor.MainActivity (server)' ~ Consumer closed input channel or an error occurred. events=0x8
10-04 21:11:42.588: E/InputDispatcher(62): channel '405a9a88 com.example.enose.sensor/com.example.enose.sensor.MainActivity (server)' ~ Channel is unrecoverably broken and will be disposed!
10-04 21:11:57.488: E/InputDispatcher(62): channel '40746548 com.example.enose.sensor/com.example.enose.sensor.MainActivity (server)' ~ Consumer closed input channel or an error occurred. events=0x8
10-04 21:11:57.488: E/InputDispatcher(62): channel '40746548 com.example.enose.sensor/com.example.enose.sensor.MainActivity (server)' ~ Channel is unrecoverably broken and will be disposed!
10-04 21:39:31.018: E/InputDispatcher(62): channel '4061f108 com.example.enose.sensor/com.example.enose.sensor.MainActivity (server)' ~ Consumer closed input channel or an error occurred. events=0x8
10-04 21:39:31.018: E/InputDispatcher(62): channel '4061f108 com.example.enose.sensor/com.example.enose.sensor.MainActivity (server)' ~ Channel is unrecoverably broken and will be disposed!
これが機能しない場合。誰かがBluetooth経由で既知のMACアドレスを持つデバイスに接続するための簡単なチュートリアルを投稿できますか?また、誰かがUUIDを取得するプロセスとその使用法を説明できますか?