tempPreRate++;
return;
}
tempPreRate=0;
try{
if(data!
=null)
{
YuvImageimage=newYuvImage(data,VideoFormatIndex,VideoWidth,VideoHeight,null);
if(image!
=null)
{
ByteArrayOutputStreamoutstream=newByteArrayOutputStream();
//在此设置图片的尺寸和质量
pressToJpeg(newRect(0,0,(int)(VideoWidthRatio*VideoWidth),
(int)(VideoHeightRatio*VideoHeight)),VideoQuality,outstream);
outstream.flush();
//启用线程将图像数据发送出去
Threadth=newMySendFileThread(outstream,pUsername,serverUrl,serverPort);
th.start();
}
}
}catch(IOExceptione){
e.printStackTrace();
}
}
值得注意的是,在调试中YuvImage可能找不到,在模拟机上无法执行该过程,但是编译后在真机中可以通过。
此外,以上传输文字字符都是采用UTF编码,在服务器端接收时进行解析时需要采用对应的编码进行解析,否则可能会出现错误解析。
Android客户端中关键的部分主要就这些,新建一个Android项目(项目名称为SocketCamera),在main布局中添加一个SurfaceView和两个按钮,如下图所示:
然后在SocketCameraActivity.java中添加代码,具体如下:
packagecom.xzy;
importjava.io.ByteArrayInputStream;
importjava.io.ByteArrayOutputStream;
importjava.io.IOException;
importjava.io.OutputStream;
importjava.io.PrintWriter;
import.Socket;
import.UnknownHostException;
importandroid.app.Activity;
importandroid.app.AlertDialog;
importandroid.content.DialogInterface;
importandroid.content.Intent;
importandroid.content.SharedPreferences;
importandroid.graphics.Rect;
importandroid.graphics.YuvImage;
importandroid.hardware.Camera;
importandroid.hardware.Camera.Size;
importandroid.os.Bundle;
importandroid.preference.PreferenceManager;
importandroid.view.Menu;
importandroid.view.MenuItem;
importandroid.view.SurfaceHolder;
importandroid.view.SurfaceView;
importandroid.view.View;
importandroid.view.WindowManager;
importandroid.view.View.OnClickListener;
importandroid.widget.Button;
publicclassSocketCameraActivityextendsActivityimplementsSurfaceHolder.Callback,
Camera.PreviewCallback{
privateSurfaceViewmSurfaceview=null;//SurfaceView对象:
(视图组件)视频显示
privateSurfaceHoldermSurfaceHolder=null;//SurfaceHolder对象:
(抽象接口)SurfaceView支持类
privateCameramCamera=null;//Camera对象,相机预览
/**服务器地址*/
privateStringpUsername="XZY";
/**服务器地址*/
privateStringserverUrl="192.168.1.100";
/**服务器端口*/
privateintserverPort=8888;
/**视频刷新间隔*/
privateintVideoPreRate=1;
/**当前视频序号*/
privateinttempPreRate=0;
/**视频质量*/
privateintVideoQuality=85;
/**发送视频宽度比例*/
privatefloatVideoWidthRatio=1;
/**发送视频高度比例*/
privatefloatVideoHeightRatio=1;
/**发送视频宽度*/
privateintVideoWidth=320;
/**发送视频高度*/
privateintVideoHeight=240;
/**视频格式索引*/
privateintVideoFormatIndex=0;
/**是否发送视频*/
privatebooleanstartSendVideo=false;
/**是否连接主机*/
privatebooleanconnectedServer=false;
privateButtonmyBtn01,myBtn02;
/**Calledwhentheactivityisfirstcreated.*/
@Override
publicvoidonCreate(BundlesavedInstanceState){
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
//禁止屏幕休眠getWindow().setFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON,
WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
mSurfaceview=(SurfaceView)findViewById(R.id.camera_preview);
myBtn01=(Button)findViewById(R.id.button1);
myBtn02=(Button)findViewById(R.id.button2);
//开始连接主机按钮
myBtn01.setOnClickListener(newOnClickListener(){
publicvoidonClick(Viewv){
//Common.SetGPSConnected(LoginActivity.this,false);
if(connectedServer){//停止连接主机,同时断开传输
startSendVideo=false;
connectedServer=false;
myBtn02.setEnabled(false);
myBtn01.setText("开始连接");
myBtn02.setText("开始传输");
//断开连接
Threadth=newMySendCommondThread("PHONEDISCONNECT|"+pUsername+"|");
th.start();
}
else//连接主机
{
//启用线程发送命令PHONECONNECT
Threadth=newMySendCommondThread("PHONECONNECT|"+pUsername+"|");
th.start();
connectedServer=true;
myBtn02.setEnabled(true);
myBtn01.setText("停止连接");
}
}});
myBtn02.setEnabled(false);
myBtn02.setOnClickListener(newOnClickListener(){
publicvoidonClick(Viewv){
if(startSendVideo)//停止传输视频
{
startSendVideo=false;
myBtn02.setText("开始传输");
}
else{//开始传输视频
startSendVideo=true;
myBtn02.setText("停止传输");
}
}});
}
@Override
publicvoidonStart()//重新启动的时候
{
mSurfaceHolder=mSurfaceview.getHolder();//绑定SurfaceView,取得SurfaceHolder对象
mSurfaceHolder.addCallback(this);//SurfaceHolder加入回调接口
mSurfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);//设置显示器类型,setType必须设置
//读取配置文件
SharedPreferencespreParas=PreferenceManager.getDefaultSharedPreferences(SocketCameraActivity.this);
pUsername=preParas.getString("Username","XZY");
serverUrl=preParas.getString("ServerUrl","192.168.0.100");
StringtempStr=preParas.getString("ServerPort","8888");
serverPort=Integer.parseInt(tempStr);
tempStr=preParas.getString("VideoPreRate","1");
VideoPreRate=Integer.parseInt(tempStr);
tempStr=preParas.getString("VideoQuality","85");
VideoQuality=Integer.parseInt(tempStr);
tempStr=preParas.getString("VideoWidthRatio","100");
VideoWidthRatio=Integer.parseInt(tempStr);
tempStr=preParas.getString("VideoHeightRatio","100");
VideoHeightRatio=Integer.parseInt(tempStr);
VideoWidthRatio=VideoWidthRatio/100f;
VideoHeightRatio=VideoHeightRatio/100f;
super.onStart();
}
@Override
protectedvoidonResume(){
super.onResume();
InitCamera();
}
/**初始化摄像头*/
privatevoidInitCamera(){
try{
mCamera=Camera.open();
}catch(Exceptione){
e.printStackTrace();
}
}
@Override
protectedvoidonPause(){
super.onPause();
try{
if(mCamera!
=null){
mCamera.setPreviewCallback(null);//!
!
这个必须在前,不然退出出错
mCamera.stopPreview();
mCamera.release();
mCamera=null;
}
}catch(Exceptione){
e.printStackTrace();
}
}
@Override
publicvoidsurfaceChanged(SurfaceHolderarg0,intarg1,intarg2,intarg3){
//TODOAuto-generatedmethodstub
if(mCamera==null){
return;
}
mCamera.stopPreview();
mCamera.setPreviewCallback(this);
mCamera.setDisplayOrientation(90);//设置横行录制
//获取摄像头参数
Camera.Parametersparameters=mCamera.getParameters();
Sizesize=parameters.getPreviewSize();
VideoWidth=size.width;
VideoHeight=size.height;
VideoFormatIndex=parameters.getPreviewFormat();
mCamera.startPreview();
}
@Override
publicvoidsurfaceCreated(SurfaceHolderholder){
//TODOAuto-generatedmethodstub
try{
if(mCamera!
=null){
mCamera.setPreviewDisplay(mSurfaceHolder);
mCamera.startPreview();
}
}catch(IOExceptione){
e.printStackTrace();
}
}
@Override
publicvoidsurfaceDestroyed(SurfaceHolderholder){
//TODOAuto-generatedmethodstub
if(null!
=mCamera){
mCamera.setPreviewCallback(null);//!
!
这个必须在前,不然退出出错
mCamera.stopPreview();
mCamera.release();
mCamera=null;
}
}
@Override
publicvoidonPreviewFrame(byte[]data,Cameracamera){
//TODOAuto-generatedmethodstub
//如果没有指令传输视频,就先不传
if(!
startSendVideo)
return;
if(tempPreRatetempPreRate++;
retur