Почему он возвращает нулевое значение? !! (клиент / серверное приложение) - PullRequest
0 голосов
/ 15 января 2010

Я задавал этот вопрос за 2 дня до этого, но я не могу его отредактировать (я не знаю почему), также я изменил некоторую часть своих уроков. Также я много раз проверял, но на самом деле я этого не знаю почему он возвращает нулевое значение (на консоли написано: Client says: null ), пожалуйста, помогите мне.

сначала я получаю текст из текстовой области, который получает текст от клиента, а затем я устанавливаю его в свою текстовую область, которая является выводом (например, фрейм чата в Yahoo Messenger), а затем я отправляю этот текст моему MainClient класс.

мое действие кнопки отправки, выполненное в моем фрейме чата: (Я проверил текст String в фрейме чата, и он не был нулевым)

private void jButton1ActionPerformed(java.awt.event.ActionEvent evt) {                                         

    submit();
    clear();
} 

  private void submit() {




    String text = jTextArea1.getText();


    jTextArea2.append(client.getCurrentName() + " : " + text + "\n");
    MainClient.setText(client.getCurrentName() + " : " + text + "\n");
}

мой класс MainClient: (часть этого)

private static String text;

public static String getText() {
    return text;
}

public static void setText(String text) {
    MainClient.text = text;
}

static boolean closed = false;

/**
 * @param args the command line arguments
 */
public static void main(String[] args) {
    String teXt = getText();
    try {


        os = new PrintWriter(c.getOutputStream(), true);


        is = new BufferedReader(new InputStreamReader(c.getInputStream()));
    } catch (IOException ex) {
        Logger.getLogger(MainClient.class.getName()).log(Level.SEVERE, null, ex);
    }


    if (c != null && is != null && os != null) {

        try {
            os.println(teXt);//send data over socket.
            String line = is.readLine();//recieve text from server.

            System.out.println("Text received: " + line);


            c.close();
        } catch (IOException ex) {
            System.err.println("read Failed");
       }
    }
}}

мой класс MainServer: (часть этого)

    try {
        BufferedReader streamIn = new BufferedReader(new InputStreamReader(client.getInputStream()));

        boolean done = false;
        String line =null;
        while (!done ) {

            line = streamIn.readLine();
            if (line.equalsIgnoreCase("bye")) {
                done = true;
            } else {
                System.out.println("Client says: " + line);
            }
        }

        streamIn.close();
        client.close();
        server.close();
    } catch (IOException e) {
        System.out.println("IO Error in streams " + e);
    }
}}

Сначала я запускаю MainServer, а затем запускаю MainClient (который покажет фрейм чата).

РЕДАКТИРОВАТЬ: пожалуйста, начните чтение с этой части: это два класса, один для графического интерфейса пользователя, а другой для клиента. (Сеть) он ничего не возвращает на консоли для сервера, поэтому он ничего не возвращает клиенту. помогите мне спасибо. мой класс GUI: (часть этого) (например, фрейм чата, который, нажав на кнопку «Отправить». Я отправлю что-то для сервера)

мой класс пользовательского интерфейса (фрейм чата), часть этого:

private void SendActionPerformed(java.awt.event.ActionEvent evt) {                                         
setButtonIsSelected(true);
submit();
clear();
} 
 private void submit() {




String text = jTextArea1.getText();


jTextArea2.append(client.getCurrentName() + " : " + text + "\n");
MainClient.setText(client.getCurrentName() + " : " + text + "\n");
}

private static boolean buttonIsSelected = false ;

public static boolean isButtonIsSelected() {
    return buttonIsSelected;
}

public static void setButtonIsSelected(boolean buttonIsSelected) {
    ChatFrame.buttonIsSelected = buttonIsSelected;
}

мой класс MainClient: (часть этого)

show a chat frame.

if ( ChatFrame.isButtonIsSelected() == true) {

    String teXt = getText();
    System.out.println(teXt);
    os.println(teXt);
    String line;
    line = is.readLine();
    System.out.println("Text received: " + line);

}

сначала я буду запускать клиентский класс, поэтому будет запускаться класс gui с именем Chat Frame.

Ответы [ 3 ]

1 голос
/ 15 января 2010

Попробуйте позвонить:

os.flush();

на вашем PrintWriter сразу после звонка:

os.println(teXt);

1 голос
/ 15 января 2010

Кажется, ваш главный клиент подключается к серверу и отправляет текст прямо при запуске, а не когда кто-то что-то вводит. Таким образом, переменный текст является нулевым.

Вы должны отправлять текст по проводам, когда пользователь нажимает кнопку и всегда получает строки с сервера. Поэтому вы должны посвятить поток (основной поток в порядке) чтению с сервера и ничего более.

Конечно, если вы используете основной поток для получения ответов сервера, вы должны быть осторожны, чтобы обновить свой пользовательский интерфейс, потому что вы не можете сделать это из любого потока. В Swing вы должны вызывать специальный метод (SwingUtilities # invokeLater, если я хорошо помню), но в AWT я не знаю.

Надеюсь, это поможет. Может быть, я не понимаю правильную точку зрения в конце концов! : D

0 голосов
/ 15 января 2010

Тривиальным решением может быть то, что ваша переменная teXt будет нулевой или пустой в момент отправки ее в сокет. Пожалуйста, вставьте System.out.println (teXt) прямо перед вашим вызовом os.println (teXt), чтобы дважды проверить, действительно ли вы что-то отправляете клиенту.

Редактировать

Итак, хитрая клиент-серверная часть работает как надо. Я думаю, что у helios есть правильный ответ в его комментариях: когда вы запускаете клиента с чем-то вроде

java -cp <your classpath> your.pckg.here.MainClient

он немедленно вызовет getText (), который возвращает ноль, потому что так инициализируется текстовое поле. Таким образом, вы присваиваете это нулевое значение teXt, и это то, что вы отправляете.

Этот код не реагирует ни на что, что вы делаете или изменяете в рамке чата.

Таким образом, решение состоит в том, чтобы перепроектировать поток в приложении так, чтобы клиент действительно отправлял что-то, если и только если нажата кнопка на фрейме чата.

Редактировать

Это очень простой, но рабочий пример системы клиент / сервер с графическим интерфейсом. Код очень плохой (плохая обработка исключений, клиент и сервер не будут завершены и должны быть «убиты», уродливый графический интерфейс), но он демонстрирует основы.

Сервер:

public class Server {

    public static void main(String[] args) throws Exception {
        ServerSocket socket = new ServerSocket(12345);
        while(true) {
            Socket client = socket.accept();
            InputStream in = client.getInputStream();
            int i = in.read();
            while (i != -1) {
                System.out.print((char) i);
                i = in.read();
            }
            System.out.println();
            in.close();
        }
    }

}

Сервер прослушивает порт 12345 и просто выводит все входящие байты в виде символов на консоль. Это будет происходить вечно (реальный сервер может быть остановлен ...)

GUI:

public class GUI extends JFrame {

    public GUI() {
        setSize(100, 100);
        Container contentPane = getContentPane();
        Button button = new Button("Press me");
        button.addActionListener(new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent e) {
                Client.send("Button pressed");          
            }
        });
        contentPane.add(button);
    }

}

Ничего, кроме рамки без названия, показывающей одну кнопку. Если вы нажмете эту кнопку, она отправит текстовое сообщение классу Client (iaw - вызовите метод Client.send со статическим текстом)

Клиент:

public class Client {

    public static void main(String[] args) throws Exception {
        GUI gui = new GUI();
        gui.setVisible(true);
    }

    public static void send(String msg) {
        try {
            Socket socket = new Socket("localhost", 12345);
            OutputStream out = socket.getOutputStream();
            out.write("Hello world".getBytes());
            out.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

}

Клиент создает и запускает великолепный графический интерфейс. И это содержит сервис отправки. По запросу (вызов метода send) он установит соединение с сервером и отправит строку в виде байтов.

Итак, смысл в том, чтобы отправить что-то, вы должны сказать клиенту сделать это. И то же самое с вашим кодом: просто установка поля в классе клиента не вызовет процедуру отправки. Реализуйте метод send и вызывайте его всякий раз, когда вам есть что отправить.

(я не включал названия пакетов и импорт в примеры, но я использовал только стандартные классы java (swing).)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...