android客户端传图给java socket服务端,客户端却收不到返回图

移动开发 码拜 6年前 (2015-05-11) 513次浏览 0个评论

写了一个Android客户端和java socket服务端。客户端把SD卡里的一张图传给服务端,服务端也收到了,也保存为一张图。接下来用服务端把保存的这张jpg图文件再通过DataOutputStream DOS=new DataOutputStream(s.getOutputStream());发给客户端。但测试了很多遍,客户端并没有收到这张图片。在看了看服务端的代码,发现执行到DOS.write(data);时,即服务端把图片数据写到DOS时就执行不下去了,不知道什么原因,求指导,在线等!

java socket服务端代码:

package newserver;

import java.io.BufferedOutputStream;
import java.io.ByteArrayOutputStream;
import java.io.DataInputStream;
import java.io.DataOutputStream;  
import java.io.File;
import java.io.FileInputStream;  
import java.io.FileOutputStream;
import java.io.IOException;  
import java.net.InetSocketAddress;  
import java.net.ServerSocket;  
import java.net.Socket;  
import java.util.ArrayList;

public class Server02 {

	//定义一个线性表,用来装新建好的socket
	public static ArrayList<Socket> socketList = new ArrayList<Socket>();

	//定义一个线性表,用来装新建好的文件名
	public static ArrayList<String> fileList = new ArrayList<String>();

	//文件名序号
	public static int no=0;

    public static void main(String[] args) throws IOException {
    
    	ServerSocket ss = new ServerSocket(40000);
    
    	while(true){
    		Socket s = ss.accept();
    		socketList.add(s);
    
    		new Thread(new ServerThread(s)).start();
    	}
    }  
}  
package newserver;

import java.io.BufferedOutputStream;
import java.io.ByteArrayOutputStream;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.net.Socket;

public class ServerThread implements Runnable{

	Socket s=null;

	public ServerThread(Socket socket){
		this.s=socket;
		System.out.println("一条线程启动");
	}

	public void run(){
		DataInputStream dis =null;
		FileOutputStream fos=null;
		DataOutputStream dos=null;
		DataOutputStream DOS =null;

		//每读取一条来自客户端的信息,都新建一个文件,文件名加1
		Server02.no++;
		//用来保存客户端发来的信息的文件夹名,并加入到顺序表里面去
		String fileName="image"+Server02.no+".jpg";
		Server02.fileList.add(fileName);

		File file = new File(fileName);

		try{
			//连接客户端的socket,为读取客户端输入做准备
			dis =new DataInputStream(s.getInputStream());
			DOS = new DataOutputStream(s.getOutputStream()); 

			ByteArrayOutputStream bytestream = new ByteArrayOutputStream();
            byte[] inputByte = new byte[1024];
            int length = 0;
            //接受客户端的输入,输入到inputByte里,再输入到bytestream里
            while ((length = dis.read(inputByte, 0, inputByte.length)) > 0) {
                bytestream.write(inputByte, 0, length);
            }
            
            fos=new FileOutputStream(file);
            //将bytestream的内容输入到jpg文件里面
            dos = new DataOutputStream(fos);
            dos.write(bytestream.toByteArray());
            dos.flush();
            
            System.out.println("可以浏览照片了");
       
       		 System.out.println("开启dos");
                //读取图片文件到FIS流
                FileInputStream FIS = new FileInputStream(Server02.fileList.get(Server02.no-1));  
                int size = FIS.available();
                
                System.out.println("size = "+size);
                byte[] data = new byte[size];  
                FIS.read(data);                             
                
                //将内容写到DOS里面,即传给客户端的DataInputStream,内容包括数组大小和图片数据
                DOS.writeInt(size);                 
                DOS.write(data);   
                System.out.println(data);
                
                DOS.flush();                                        
                DOS.close();                                 
                FIS.close();
                
                dos.close();
                
                dis.close(); 
 

		}catch(IOException e){

		}
	}

android客户端代码:

package com.example.phototest2;

import java.io.ByteArrayOutputStream;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.File;

import java.io.IOException;
import java.net.Socket;


import android.app.Activity;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.Bundle;
import android.os.Environment;
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.Toast;
import android.view.View.OnClickListener;

public class MainActivity extends Activity {

	private Bitmap bitmap,bmp;
	private ImageView imageView02;
	private Button button01,button02;
	private final String fileName=Environment.getExternalStorageDirectory().getPath()+"/myImage/20150408_113803.jpg";

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);

		imageView02 = (ImageView)findViewById(R.id.image02);
		button01=(Button)findViewById(R.id.Button01);
        button02 = (Button)findViewById(R.id.Button02);
	       
	    button02.setOnClickListener(new OnClickListener(){
				public void onClick(View arg0) {

			        File file=new File(fileName);

					if(file.exists()){
						bitmap=BitmapFactory.decodeFile(fileName);
						Toast.makeText(MainActivity.this, "图片存在", Toast.LENGTH_LONG).show();
					}
					else{
						Toast.makeText(MainActivity.this, "图片不存在", Toast.LENGTH_LONG).show();
					}

					//imageView02.setImageBitmap(bitmap);

					new Thread(){

						Socket socket=null;

						@Override
						public void run(){

							try{
							socket = new Socket("110.64.90.157",40000);

							DataOutputStream out = new DataOutputStream(socket.getOutputStream()); 

							ByteArrayOutputStream baos = new ByteArrayOutputStream();
							//读取图片到ByteArrayOutputStream
							bitmap.compress(Bitmap.CompressFormat.PNG, 100, baos);
							byte[] bytes = baos.toByteArray();
							out.write(bytes);
							out.flush();
							//System.out.println("bytes--->"+bytes);
							out.close();
							//原来out.close();位置

							DataInputStream dataInput = new DataInputStream(socket.getInputStream());    
				            int size = dataInput.readInt();    
				            byte[] data = new byte[size];    
				            int len = 0;    
				            while (len < size) {    
				                len += dataInput.read(data, len, size - len);    
				            }    
				            //ByteArrayOutputStream outPut = new ByteArrayOutputStream();    
				            bmp = BitmapFactory.decodeByteArray(data, 0, data.length);
				            
				            
				            //dataInput.close();

							}catch(IOException e){
								e.printStackTrace(); 
							}
							finally {    
					            try {    
					                socket.close();
					                Log.v("wei", "socket关闭");
					            } catch (IOException e) {    
					                e.printStackTrace();    
					            }
							}
						}
					}.start();

				}
			});
	    
	    button01.setOnClickListener(new OnClickListener(){
	    	public void onClick(View sourse) {
	    		imageView02.setImageBitmap(bmp);
	    	}
	    });
	        
	      
	}
}

android布局有两个Button,Button01用于显示后来服务端发回来的照片.,Button02用于上传图片到服务端。
剩下的靠各位兄弟姐妹了!

求助!!
45分
粗略一看,应该是bmp是在线程里赋值的原因造成的

button01.setOnClickListener(new OnClickListener(){
            public void onClick(View sourse) {
// 断点这里,看看bmp赋值是否正确
                imageView02.setImageBitmap(bmp);
            }
        });
引用 2 楼 lyw985 的回复:

粗略一看,应该是bmp是在线程里赋值的原因造成的

button01.setOnClickListener(new OnClickListener(){
            public void onClick(View sourse) {
// 断点这里,看看bmp赋值是否正确
                imageView02.setImageBitmap(bmp);
            }
        });

虽然在里面赋值,但我是等上传完照片,我才按Button1显示bmp的,我已经等了足够久的时间了,但还是没有东西。我测试了一下,发现客户端在DataInputStream dataInput = new DataInputStream(socket.getInputStream()); 这里停住了,不知道什么原因。

50分
引用 2 楼 lyw985 的回复:

粗略一看,应该是bmp是在线程里赋值的原因造成的

button01.setOnClickListener(new OnClickListener(){
            public void onClick(View sourse) {
// 断点这里,看看bmp赋值是否正确
                imageView02.setImageBitmap(bmp);
            }
        });

我也弄个相似的程序,也写 不出来,但是跟楼主的不一样地方是貌似就是bmp的值不知道,DataInputStream dataInput = new DataInputStream(socket.getInputStream())我应该运行出来了,因为后面的size值就是我发送的大小,请问这该怎么办?

引用 4 楼 yemao_guyue 的回复:
Quote: 引用 2 楼 lyw985 的回复:

粗略一看,应该是bmp是在线程里赋值的原因造成的

button01.setOnClickListener(new OnClickListener(){
            public void onClick(View sourse) {
// 断点这里,看看bmp赋值是否正确
                imageView02.setImageBitmap(bmp);
            }
        });

我也弄个相似的程序,也写 不出来,但是跟楼主的不一样地方是貌似就是bmp的值不知道,DataInputStream dataInput = new DataInputStream(socket.getInputStream())我应该运行出来了,因为后面的size值就是我发送的大小,请问这该怎么办?

我解决了我的问题了,我的原因是直接通过setimagebitmap方法来改变Imageview的图片是不可以的,应该通过handler来传递调用,但你程序貌似没有我出现的问题,我也是新手,所以好多还不懂,求大神们多指点!希望大神们给个QQ,让我可以多请教!谢谢

5分
请将图片转化为base64
问题已经解决了,前些时间因为比较忙,也忘记了结贴。
问题的原因是:客户端在向服务端传送数据后,在第76行(android程序)中把输出流关闭了。这时客户端与服务端相连的socket也关闭了。这就会导致后来在服务端程序中使用这个socket的服务端输出流向客户端传数据时,找不到这个socket了,所以传不过去了。
解决办法:在android程序第76行把out.close();改为socket.shutdownOutputStream();从而解决了关闭输出流就关闭了socket的问题。
抽空特意来结贴,希望我们互相学习,共同进步。
引用 5 楼 yemao_guyue 的回复:
Quote: 引用 4 楼 yemao_guyue 的回复:
Quote: 引用 2 楼 lyw985 的回复:

粗略一看,应该是bmp是在线程里赋值的原因造成的

button01.setOnClickListener(new OnClickListener(){
            public void onClick(View sourse) {
// 断点这里,看看bmp赋值是否正确
                imageView02.setImageBitmap(bmp);
            }
        });

我也弄个相似的程序,也写 不出来,但是跟楼主的不一样地方是貌似就是bmp的值不知道,DataInputStream dataInput = new DataInputStream(socket.getInputStream())我应该运行出来了,因为后面的size值就是我发送的大小,请问这该怎么办?

我解决了我的问题了,我的原因是直接通过setimagebitmap方法来改变Imageview的图片是不可以的,应该通过handler来传递调用,但你程序貌似没有我出现的问题,我也是新手,所以好多还不懂,求大神们多指点!希望大神们给个QQ,让我可以多请教!谢谢

你所说的不能通过setimagebitmap方法来改变Imageview的图片,是因为你在其他线程里调用,修改UI必须在线程UI中修改的。


CodeBye 版权所有丨如未注明 , 均为原创丨本网站采用BY-NC-SA协议进行授权 , 转载请注明android客户端传图给java socket服务端,客户端却收不到返回图
喜欢 (0)
[1034331897@qq.com]
分享 (0)

文章评论已关闭!