Plugin: Advanced Sessions
I was making a multiplayer lobby. and I have a list of players. the list contains of buttons with the user’s name on the button. I populate the list by getting the game state and then getting the player array.
(this is so I can get the unique IDs from players.)
I would like it to create a widget on the other player’s screen when I click on their button. (like if you were playing a game and you want to request to trade items or something.)
the only way I can think of to do this is get a reference to the player controller of the person’s button who we clicked on and then tell their controller to create a widget.
my problem is that I cant figure out a way to reference the other player’s controller.
Don’t try to reference the other player’s Controller. Controllers are connections owned by the machine they live on, and therefore can’t be referenced by another machine (with a sort of kind of exception on the Server itself since the Server has to have the connections to all the Players that are in its game).
To do what you’re trying to do, which I think is to have the other client machine’s player’s HUD pop up a widget, you are trying to get the PlayerState’s PlayerController so you can send it an RPC or change a variable or Notify it or something, so it will run a function to pop up that widget on their computer right?
This makes sense because the Controller is the connection to that client’s computer.
What I’ve found though is that while PlayerControllers have PlayerStates, the PlayerStates don’t seem to have a reference back to their controller. This might be because PlayerControllers are not replicated across the network and that would cause confusion.
So what I do (and I don’t know if this is the “right” way) is on the Server, I loop through all the PlayerControllers until I find the one with the PlayerState which has the matching Player ID for the player I’m trying to send the Client RPC to.
That Client RPC can be the thing that pops up the widget, and can take parameters.
If someone knows a better way, PLEASE let us know! It’s been a hassle for me, and if there are 100+ players on the server we don’t want to have to loop through them all every time, I think.
I know what your saying. Thank you! but could you show me a sense of how to do this?
I am fairly new to unreal engine’s networking and don’t quite understand replication, multicast etc.
It would be most appreciated! Thank you in advance!
Maybe we can make this simple. The Player you want to trade with has a Pawn, right? Why not just target the Pawn, get the Controller of the pawn, and call a Client RPC from the Server, onto that Pawn, passing the data of what item you want to trade, etc.?
Client to Server: The first client makes a RunOnServer event on his own player controller or pawn
Server to Other Clients: The Server forwards the call back to the other clients using a Multicast event.
The key is that a client can only issue a RunOnServer event on objects the client owns. The safe bet is the client PlayerController but the Pawn that the client possesses or objects owned by that pawn will also work.
You can simply use the GetOwner node for the player state and then cast to the player controller class of your current level. Worked perfectly fine for me.
If you need the player controller in order to cast to a pawn, you can use the node called pawn private (without context sensitive on) and connect it to ForEachLoop at ArrayElements, from there you can cast to your pawn and from the pawn cast to controller. Hope it’s helpfull