发送图片类SendImage
import java.io.File;
import java.io.FileInputStream;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;
import java.util.Scanner;
/***
* 发送图片类
*/
public class SendImage {
private static final int SINGLE_LENGTH=63*1024;//单个包发送大小64K
private static final int SINGLE_CONTENT=63*1024-24;//单个包实际内容
//long转字节
public static byte[] longToBytes(long l) {
byte[] result = new byte[8];
for (int i = 7; i >= 0; i--) {
result[i] = (byte)(l & 0xFF);
l >>= 8;
}
return result;
}
//字节数组转long
public static long bytesToLong(byte[] b) {
long result = 0;
for (int i = 0; i < 8; i++) {
result <<= 8;
result |= (b[i] & 0xFF);
}
return result;
}
/***
* (折包)
* 对单个文件进行拆包
* 单个包的格式:拆成几个包(long)+当前在第几个包(long)+当前包的数据长度(long)+文件内容 *
* @param filePath
* @return
*/
private static byte[][] getFileBytes(String filePath){
try{
int content_length=SINGLE_CONTENT;
File file=new File(filePath);
if(file.exists()){
FileInputStream fileInputStream=new FileInputStream(file);
long fileLength=0;
if(file.length()%content_length==0){
fileLength=file.length()/content_length;
}else{
fileLength=file.length()/content_length+1;
};
byte result[][]=new byte[(int)fileLength][SINGLE_LENGTH];
for(int i=0;i<fileLength;i++){
byte[]buf=new byte[SINGLE_LENGTH];
//插入拆包大小
byte[] temp=longToBytes(fileLength);
System.arraycopy(temp,0,buf,0,8);
//插入文件位置
temp=longToBytes((long)i);
System.arraycopy(temp,0,buf,8,8);
int readLength=fileInputStream.read(buf,24,content_length);
//插入当前包的内容长度
temp=longToBytes((long)readLength);
System.arraycopy(temp,0,buf,16,8);
result[i]=buf;
}
fileInputStream.close();
return result;
}
}catch (Exception e){
e.printStackTrace();
}
return null;
}
public static void main(String[] args) {
try {
System.out.println("请输入图片文件夹路径,如D:\\:");
Scanner scanner=new Scanner(System.in);
String dirPath=scanner.next();
//查询目录下有多少个文件
File file[]=new File(dirPath).listFiles();
for(int i=0;i<file.length;i++){
System.out.println("正在发送文件:"+file[i].getName());
//图版转化为字节数组
byte[][] temp=getFileBytes(file[i].getPath());
//发送数据包
DatagramSocket socket = new DatagramSocket();
for(int j=0;j<temp.length;j++){
//将数据打包
DatagramPacket packet = new DatagramPacket(temp[j], temp[j].length, InetAddress.getByName("127.0.0.1"), 8080);
socket.send(packet);
//防止发送包过快,出现丢包
Thread.sleep(500);
System.out.println("发送文件第"+j+"段");
}
socket.close();
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
接收图片类ReceiveImage
import javax.swing.*;
import java.awt.*;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.nio.ByteBuffer;
import java.util.ArrayList;
import java.util.Arrays;
/***
* 接收图片类
*/
public class ReceiveImage extends JFrame {
private static final int SINGLE_LENGTH = 63 * 1024;//单个包发送大小64K
private static final int SINGLE_CONTENT = 63 * 1024 - 24;//单个包实际内容
private static final long serialVersionUID = 1L;
private static ReceiveImage receiveImage=null;
private static java.util.List<JLabel> labels;
private int showIndex=0;//显示在第几个图片上
//接收数据方法
private void receiveData() {
try {
// 定义一个接收端,并且指定了接收的端口号
DatagramSocket socket = new DatagramSocket(8080);
byte receivebuf[][]=null;
int receivesize=0;
while (true) {
//每次接收一个数据包
byte[] buf = new byte[SINGLE_LENGTH];
// 解析数据包
DatagramPacket packet = new DatagramPacket(buf, buf.length);
socket.receive(packet);
String ip = packet.getAddress().getHostAddress();
buf = packet.getData();
int dataPacketSize=(int) bytesToLong(Arrays.copyOfRange(buf,0,8));;//数据包的长度
int fileIndex=(int) bytesToLong(Arrays.copyOfRange(buf,8,16));
if(receivebuf==null){
receivebuf=new byte[dataPacketSize][SINGLE_LENGTH];
}
receivebuf[fileIndex]=buf;
receivesize++;
//判断数据是否接收完成
if(dataPacketSize==receivesize){
//显示图片
ImageIcon image =bytesTOFile(receivebuf);
//接收完成显示图片
image=new ImageIcon(image.getImage().getScaledInstance(getWidth()/3, getHeight()/3, Image.SCALE_DEFAULT));
receiveImage.labels.get((showIndex++%9)).setIcon(image);
receivebuf=null;
receivesize=0;
}
// String data = new String(buf, 0, packet.getLength());
System.out.println("收到 " + ip + " 发来的消息" );
}
} catch (Exception e) {
e.printStackTrace();
}
}
//long转字节
public static byte[] longToBytes(long l) {
byte[] result = new byte[8];
for (int i = 7; i >= 0; i--) {
result[i] = (byte)(l & 0xFF);
l >>= 8;
}
return result;
}
//字节数组转long
public static long bytesToLong(byte[] b) {
long result = 0;
for (int i = 0; i < 8; i++) {
result <<= 8;
result |= (b[i] & 0xFF);
}
return result;
}
/***
* (组包)
* 字节数组转化为文件存储
*
* 单个包的格式:拆成几个包(long)+当前在第几个包(long)+当前包的数据长度(long)+文件内容
* @param fileBytes 文件数组
* @param filePath
*/
private ImageIcon bytesTOFile(byte[][] fileBytes){
try{
int dataPacketSize=0;//数据包的长度
//int fileIndex=-1;//文件位置
int contextSize=0;//单人上包的内容大小
ByteBuffer buffer =null;
for(int i=0;i<fileBytes.length;i++){
if(i==0){
dataPacketSize=(int) bytesToLong(Arrays.copyOfRange(fileBytes[i],0,8));
buffer= ByteBuffer.allocate(dataPacketSize*SINGLE_LENGTH);
}
//fileIndex=(int) bytesToLong(Arrays.copyOfRange(fileBytes[i],8,16));
contextSize=(int) bytesToLong(Arrays.copyOfRange(fileBytes[i],16,24));
buffer.put(fileBytes[i],24,contextSize);
}
ImageIcon bi1 = new ImageIcon(buffer.array());
return bi1;
/* FileOutputStream fileOutputStream=new FileOutputStream(filePath);
fileOutputStream.write(buffer.array());
fileOutputStream.close();*/
}catch (Exception e){
e.printStackTrace();
}
return null;
}
public static void main(String[] args) {
try {
receiveImage= new ReceiveImage();
receiveImage.setLayout(new GridLayout(3,3));
receiveImage.setTitle("测试图片简单显示");
receiveImage.setSize(300, 300);
receiveImage.setDefaultCloseOperation(DISPOSE_ON_CLOSE);
labels=new ArrayList<JLabel>();
for(int i=0;i<9;i++){
JLabel label = new JLabel();
labels.add(label);
receiveImage.add( label);
}
receiveImage.setVisible(true);
new Thread(new Runnable() {
@Override
public void run() {
receiveImage.receiveData();
}
}).start();
} catch (Exception e) {
System.out.println("初始化失败" + e.getMessage());
e.printStackTrace();
}
}
}
发送方:
?接收方:
?
|