在JavaFx中编码UDP通信

时间:2016-12-23 17:49:07

标签: java udp

我在JavaFx中编写UDP通信时遇到问题。

代码能够发送消息,但无法接收消息。

我应该在源代码中修改以接收消息?

以下是源代码:

public class JavaFXApplication10 extends Application {

public DatagramSocket receivesocket; 
public DatagramPacket receivepacket; 
public DatagramSocket sendsocket;    
public DatagramPacket sendpacket;   
public InetSocketAddress remoteAdress;

public Label     label_IP;
public TextField tx_IP;
public Label     label_SENDPORT;
public Label     label_RECEIVEPORT;
public TextField tx_SENDPORT;
public TextField tx_RECEIVEPORT;
public Button    bt_co;
public Button    bt_start ;
private String    message; 
private XYChart.Series series; 
private Timeline timer; 
private static String    IP = "192.168.121.23"; 
private static Integer SENDPORT = 12345;       
private static Integer RECEIVEPORT = 12345;    
public double time_counter=0.0;
private String text;
private byte[] b;
@Override

public void start(Stage stage) throws Exception{


    /* text */
     tx_IP = TextFieldBuilder.create().text(IP).build();

    /* text */
    tx_SENDPORT = TextFieldBuilder.create().text(""+SENDPORT).build();

    /* text */
    tx_RECEIVEPORT = TextFieldBuilder.create().text(""+RECEIVEPORT).build();

    /*button */
    bt_co = ButtonBuilder.create().text("Connection")
            .prefWidth(200)
            .alignment(Pos.CENTER)
            .id("connect")
            .build();

    /* button_start */
    bt_start = ButtonBuilder.create().text("START")
            .id("start")
            .build();


    /* timer */
     timer = new Timeline(new KeyFrame(Duration.millis(1000), new EventHandler<ActionEvent>(){
        @Override
        public void handle(ActionEvent event) {

           time_counter = time_counter+1; // time

        }
    }));
    timer.setCycleCount(Timeline.INDEFINITE);
    timer.play();

    /*figure*/
    stage.setTitle("Line Chart Sample");

    final NumberAxis xAxis = new NumberAxis();
    final NumberAxis yAxis = new NumberAxis();
    xAxis.setLabel("Time [s]");
    yAxis.setLabel("Force [N]");
    //creating the chart
    final LineChart<Number,Number> lineChart = 
            new LineChart<Number,Number>(xAxis,yAxis);

    lineChart.setTitle("");

    //defining a series
    series = new XYChart.Series();
    series.setName("Force");
    series.getData().add(new XYChart.Data(0.0,0.0));
     lineChart.getData().add(series);




    HBox root1 = HBoxBuilder.create().spacing(100).children(tx_IP ,tx_SENDPORT,tx_RECEIVEPORT).build();
    HBox root2 = HBoxBuilder.create().spacing(50).children(bt_co).build();
    HBox root3 = HBoxBuilder.create().spacing(25).children(bt_start).build();
    VBox root4 = VBoxBuilder.create().spacing(25).children(root1,root2,root3,lineChart).build();


    Scene scene = new Scene(root4);

    recieve_UDP();


    scene.addEventHandler(ActionEvent.ACTION,actionHandler);



    stage = StageBuilder.create().width(640).height(640).scene(scene).title(" ").build();
    stage.show(); 
}


private void recieve_UDP() throws SocketException, IOException {


    ScheduledService<Boolean> ss = new ScheduledService<Boolean>()
    {
        @Override
        protected Task<Boolean> createTask()
        {

            Task<Boolean> task = new Task<Boolean>()
            {
                @Override
                protected Boolean call() throws Exception
                {
                  receivesocket = null;

                   byte[] receiveBuffer = new byte[1024];
                   receivepacket = new DatagramPacket(receiveBuffer, receiveBuffer.length);
                   receivesocket = new DatagramSocket(RECEIVEPORT);


                   receivesocket.receive(receivepacket);
                   message = new String(receivepacket.getData(),0, receivepacket.getLength());

                   System.out.println(message);



                   receivesocket.close();
                  return true;
                };
            };


             return task;           
        }

    };
    ss.start();
}



EventHandler<ActionEvent> actionHandler = new EventHandler<ActionEvent>(){
    public void handle (ActionEvent e){


        //////////////////////////////////////////////////////////////////////////////  
        Button src =(Button)e.getTarget();
        text = src.getId(); 
        System.out.println(text);
        b = new byte[5];

        if(text == "connect"){

          String text_IP = tx_IP.getText(); 

          label_IP.setText(text_IP);

          IP = text_IP; 


          String text_SENDPORT = tx_SENDPORT.getText(); 


          label_SENDPORT.setText(text_SENDPORT);

          SENDPORT = Integer.parseInt( text_SENDPORT);

          String text_RECEIVEPORT = tx_RECEIVEPORT.getText(); 

          label_RECEIVEPORT.setText(text_RECEIVEPORT);

          RECEIVEPORT = Integer.parseInt(text_RECEIVEPORT);

        }
        else{


               remoteAdress = new InetSocketAddress(IP, SENDPORT);

       sendsocket = null;


               try {
                   sendsocket = new DatagramSocket();
               } catch (SocketException ex) {
                  Logger.getLogger(JavaFXApplication10.class.getName()).log(Level.SEVERE, null, ex);
               }

               }
               if(text=="start"){

                     b[0] = (byte)0x02;
                     text ="OK";   


               }

               else{

               }


        Send_UDP();
         /////////////////////////////////////////////////////// 
    }
};
public void Send_UDP(){

    /////////////////////////////////////////////////////// 
if(text=="OK"){

            sendpacket = new DatagramPacket(b, b.length,remoteAdress);

            try {

                sendsocket.send(sendpacket);
            } catch (IOException ex) {
                Logger.getLogger(JavaFXApplication10.class.getName()).log(Level.SEVERE, null, ex);
            }

            sendsocket.close();
            text="";

            }
        else {}
        /////////////////////////////////////////////////////// 

}


public static void main(String[] args) {
    launch(args);
}
}

1 个答案:

答案 0 :(得分:2)

您的代码非常模糊,也许我不了解所有这些代码块的目的,但我可以告诉您UDP通信非常简单,让我先介绍一下UDP通信的工作方式:

UDP通信复习

请注意,我仅使用下面的一些代码片段进行演示,所以请不要看完整性,完整的代码可以在我最后粘贴的代码中找到。

  • UDP可用于单播和多播通信。如果UDP用于单播通信,那么将始终有UDP客户端从UDP服务器请求某些内容,但是如果UDP用于多播通信,则UDP服务器将多播/广播该消息到所有侦听UDP客户端。
  • 我现在将详细讨论UDP单播)UDP服务器将在网络端口上侦听客户端请求DatagramSocket socket = new DatagramSocket(8002); socket.receive(packet);

  • UDP客户端希望与UDP服务器通信,因此它会打开DatagramSocket并在其上发送DatagramPacketDatagramPacket将包含UDP服务器的端点。

  • 一旦UDP客户端使用socket.send(packet);发送了消息,它就会准备使用socket.receive(packet);({em>我认为你缺少的地方)最重要的是要理解的是,如果客户端没有准备接收那么它将无法获得UDP服务器将发送的内容,因为在UDP的情况下UDP客户端和UDP服务器之间没有连接,因此UDP必须在发送消息后收听
  • UDP服务器将从UDP客户端接收请求,将处理该请求并将使用sendingDatagramSocket.send(packet);发送。它将使用UDP客户端的响应和端点准备DatagramPacket
  • 正在侦听的UDP客户端,如上面步骤socket.receive(packet);中所述,将从UDP服务器获得响应。 这里需要注意的重要一点是,如果UDP客户端没有监听或者没有在发出请求时打开它所打开的同一个端口(基本上使用相同的DatagramSocket对象来发送请求)那么UDP客户端永远不会收到任何UDP服务器发送

回答OP的问题

主要问题是Send_UDP只发送但未收到,recieve_UDP只收到但不发送。

所以,基本上你需要在UDP客户端和UDP服务器上发送和接收,只是反之亦然,但你需要做两件事。

示例UDP服务器和UDP客户端

UDP客户端:

import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;
import java.util.Date;

public class SimpleUDPClient {
    public static void main(String[] args) throws IOException {

        // get a datagram socket
        DatagramSocket socket = new DatagramSocket();
        System.out.println("### socket.getLocalPort():" + socket.getLocalPort() + " | socket.getPort(): " + socket.getPort());

        // send request
        byte[] buf = "Hello, I am UDP client".getBytes();
        InetAddress address = InetAddress.getByName("localhost");
        DatagramPacket packet = new DatagramPacket(buf, buf.length, address, 8002);
        socket.send(packet);

        // get response
        packet = new DatagramPacket(buf, buf.length);
        System.out.println("Waiting to receive response from server." + new Date());
        socket.receive(packet);
        System.out.println("Got the response back from server." + new Date());

        // display response
        String received = new String(packet.getData());
        System.out.println("Quote of the Moment: " + received);

        socket.close();
    }
}

UDP服务器:

import java.io.*;
import java.net.*;
import java.util.*;

public class SimpleUDPServer {

    public static void main(String[] args) throws SocketException, InterruptedException {
        DatagramSocket socket = new DatagramSocket(8002);

        while (true) {
            try {
                byte[] buf = new byte[256];

                // receive request
                DatagramPacket packet = new DatagramPacket(buf, buf.length);
                socket.receive(packet);

                System.out.println("### socket.getLocalPort():" + socket.getLocalPort() + " | socket.getPort(): " + socket.getPort());

                // figure out response
                String dString = "Server is responding:  asd  asdd";
                buf = new byte[256];
                buf = dString.getBytes();

                // send the response to the client at "address" and "port"
                InetAddress address = packet.getAddress();
                int port = packet.getPort();
                System.out.println("Data from client: " + new String(packet.getData()));
                packet = new DatagramPacket(dString.getBytes(), dString.getBytes().length, address, port);
                System.out.println("### Sending for packet.hashCode(): " + packet.hashCode() + " | packet.getPort(): " + packet.getPort());

                //Thread.sleep(5000);

                System.out.println("Now sending the response back to UDP client.");

                DatagramSocket sendingDatagramSocket = new DatagramSocket();
                sendingDatagramSocket.send(packet);
                sendingDatagramSocket.close();
                System.out.println("I am done");
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

}

进一步阅读

我强烈建议阅读this Java教程,如果不完整,那么至少&#34;编写数据报客户端和服务器&#34;部分。