之前寫模擬器和pc機通信沒有遇到過多大問題,這兩天想做一個把Socket通信的服務端和客戶端都用Android模擬器實現,有點小麻煩,蒐集一些資料,也試用很多方法,最後終於實現了模擬器之間的鏈接:
第一步:首先是創建兩個模擬器:cmd下命令創建或在eclispe中創建avd都可以實現,這裏不多說
第二步:啓動兩個模擬器
第三步:查看模擬器設備是否正常啓動
在命令行中輸入adb devices (前提啓動模擬器)
第四步:選擇一個模擬器作爲服務器,假如選擇emulator-5554 device, 客戶端爲emulator-5556 device
在cmd中執行如下命令:telnet localhost 5554 進入如下界面:
然後繼續執行:redir add tcp:8192:8191 作下重定向
注意:如果telnet localhost 5554命令不識別時,請到控制面板安裝Telnet客戶端
第五步:編寫服務端代碼
public class MySocketServerActivity extends Activity {
//座標值
float event_x=0;
float event_y=0;
public static final int SERVERPORT = 8191; //注意這裏和上面重定向的配置是有關係的。
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(new MySurface(this));
new MyServerThread().start();
}
@Override
public boolean onTouchEvent(MotionEvent event) {
event_x=event.getX();
event_y=event.getY();
System.out.println("獲得座標["+event_x+","+event_y+"]");
return super.onTouchEvent(event);
}
//啓動服務器線程
class MyServerThread extends Thread{
@Override
public void run() {
try {
System.out.println("AAAAAAAAAAAAAAAA1");
ServerSocket serverSocket = new ServerSocket(SERVERPORT);
System.out.println("AAAAAAAAAAAAAAAA2");
while (true) {
Socket client = serverSocket.accept();
//寫入座標值
OutputStream os=client.getOutputStream();
OutputStreamWriter osw=new OutputStreamWriter(os);
BufferedWriter bw=new BufferedWriter(osw);
bw.write("服務器座標信息:["+event_x+","+event_y+"]");
bw.close();
}
}catch(Exception e) {
System.out.println("S: Error");
e.printStackTrace();
}
}
}
}
class MySurface extends SurfaceView implements SurfaceHolder.Callback{
private SurfaceHolder holder;
public MySurface(Context context) {
super(context);
holder= getHolder();
holder.addCallback(this);
}
@Override
public void surfaceChanged(SurfaceHolder holder, int format, int width,
int height) {
}
@Override
public void surfaceCreated(SurfaceHolder holder) {
Canvas canvas=holder.lockCanvas();
Paint paint=new Paint();
paint.setColor(Color.RED);
canvas.drawRect(10, 10, 150, 80, paint);
paint.setColor(Color.WHITE);
canvas.drawText("座標測試區", 40, 30, paint);
holder.unlockCanvasAndPost(canvas);
}
@Override
public void surfaceDestroyed(SurfaceHolder holder) {
// TODO Auto-generated method stub
}
}
客戶端代碼:
public class MySocketClient extends Activity {
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
try {
Socket socket = new Socket("10.0.2.2", 8192);//注意這裏也是和上面重定向的配置是有關係的。而且這裏的地址必須是10.0.2.2
InputStream is=socket.getInputStream();
InputStreamReader isr=new InputStreamReader(is);
BufferedReader br=new BufferedReader(isr);
String msg=br.readLine();
Toast.makeText(this, "獲取服務器傳來的座標:"+msg,Toast.LENGTH_LONG).show();
} catch (UnknownHostException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
啓動服務端程序,啓動客戶端程序
注意:兩個程序的AndroidManifest.xml都必須加上下面這個權限:
<uses-permission android:name="android.permission.INTERNET"></uses-permission>
如果想查看程序執行過程 :
在cmd中執行如下命令
執行 adb -s emulator-5554 shell
然後執行logcat,可以查看執行log信息
啓動客戶端: