-1

I know this problem has been asked previously, but I can't realize how to send an object more than one time with an ObjectOutputStream, I tried what people said in this forum. The thing is I'm developing a Snake game in Java using multithreading and sockets, I have already drew the two snakes, but I can only send one time the snake from one to other snake, so, when I tried to send another time I got and StreamCorruptedException. Here is my code:

This method is in my Snake class, I have read that an ObjectOutputStrean cannot be initialized more than one time, but ¿How can I send the snake object more than one time?, It has turned very confused to me:

 public void sendSnake()
 {
    try
    {
        outputStream=socket.getOutputStream();
        oos=new ObjectOutputStream(outputStream);
        oos.writeObject(snakeBody);
    }catch(IOException ioe)
    {
        ioe.printStackTrace();
    }    
}

It is the part of my code that is the problem. Thanks.

Here is what I'm doing in a do while loop:

 try
 {
      this.sendSnake();
      this.receiveListSnakes();

            for(int i=0; i<listaSnakes.size(); i++)
            {
                for(int j=0; j<listSnake.get(i).tam(); j++)
                {
                    mostrar(listSnake.get(i).take(j).part); //this is for display de snake
                }
            }
 }catch(IOException ioex)
 {
     ioex.printStackTrace();
 }

 if( op.equals("up") ) 
 {
     posy--;
     ...


 public Snake(JFrame screen)
 {
      //above I have created the Socket
      socket=new Socket(ipClient, port);


      outputStream=socket.getOutputStream();
      oos=new ObjectOutputStream(outputStream);

 }
Pepe
  • 27
  • 1
  • 1
  • 7

2 Answers2

1

You could construct the ObjectOutputStream once and save the reference as a field. Also, you should flush(). Assuming you have a class Snake I would construct by passing in the socket.getOutputStream() like

private ObjectOutputStream oos;
public Snake(OutputStream os) {
  oos = new ObjectOutputStream(os);
}

public void sendSnake()
{
  try {
    oos.writeObject(snakeBody);
  } catch(IOException ioe) {
    ioe.printStackTrace();
  } finally {
    oos.flush();
  } 
}

And then you can call sendSnake with your Snake instance multiple times,

Snake s = new Snake(socket.getOutputStream());
s.sendSnake();
s.sendSnake();
Elliott Frisch
  • 198,278
  • 20
  • 158
  • 249
  • That's a good idea, but when I do it, the snake is sended in the same state, that is my snake is sended in the same positions because the OutoutStream is created only one time :C – Pepe Nov 07 '14 at 03:22
  • @Pepe Perhaps you should update your `Snake` before calling `sendSnake()` a second time. You didn't include much code to go on. But as you have repeatedly noted you should really create the `OutputStream` only once. – Elliott Frisch Nov 07 '14 at 03:36
  • I have included more code, whe I call sendSnake function I'm receiving a list with the snakes in the game, and then I make the nedeed operations to move the snake en with each iteration I'm sending the snake with new positions – Pepe Nov 07 '14 at 03:49
  • Still should work fine with my change above. How are you constructing `Snake`? – Elliott Frisch Nov 07 '14 at 03:53
  • Actually I'm doing everything in my Snake class, here I have all the instructions for the game, let me post this part – Pepe Nov 07 '14 at 03:54
0

You must use the same ObjectOutputStream for the life of the socket. More accurately, you must use ObjectOutputStream and ObjectInputStream in pairs: when you construct one you must construct the other at the peer. However this is basically impossible to co-ordinate so the single ObjectInput/OutputStream rule applies.

The Snake shouldn't send itself, and shouldn't be constructed or construct itself with a Socket [or OutputStream of any kind, contrary to other answers here]. The entity that is sending the Snake (or anything else) should own the socket and the output stream and should do the writing.

user207421
  • 305,947
  • 44
  • 307
  • 483
  • In my snake class I have an object from queueSnake class, so, I'm sending the queueSnake object not the Snake, the snake is the class in which I'm working with my queueSnake object, I have been really confused for a long time with this – Pepe Nov 07 '14 at 04:11
  • Sounds even more upside down. The Snake shouldn't know about the queue it is in, the socket it is being sent over, or the `ObjectOutputStream` that's being used to send it. – user207421 Nov 07 '14 at 04:54