I'm trying to design a vue.js app that updates data about the state of a game upon receiving a "new_state" message from a socket. The socket is implemented using django channels.
This is what the code looks like:
const ws_scheme = window.location.protocol == "https:" ? "wss" : "ws"
const gameSocket = new WebSocket(
ws_scheme +
'://'
+ window.location.host
+ '/ws/play/'
+ game_id
+ '/'
)
let vue = new Vue({
el: '#app',
data: {
current_turn: 0,
last_turn: -1,
current_card: 0,
last_card: -1,
number_of_stacked_cards: 0,
last_amount_played: 0,
won_by: -1,
my_cards: [],
other_players_data: {},
},
created() {
gameSocket.onmessage = function(e) {
data = JSON.parse(e.data)
this.current_turn = data.state.current_turn
this.last_turn = data.state.last_turn
// ... update the other data
};
},
});
When I receive the message, logging the data makes it apparent that I'm receiving correct information. However, if I go and type vue.current_turn
after receiving the message, it's still 0
instead of the new value; same for all the other members of the data
object.
I tried with vue.current_turn = data.state.current_turn
and it does work this way, but obviously it should work with this
.
What's wrong with my code?
And generally speaking, what's the best way of acplishing what I'm after, i.e. updating internal data variables upon receiving messages from a socket?
I have to do with without using the socket.io library, which isn't supported by channels.
I'm trying to design a vue.js app that updates data about the state of a game upon receiving a "new_state" message from a socket. The socket is implemented using django channels.
This is what the code looks like:
const ws_scheme = window.location.protocol == "https:" ? "wss" : "ws"
const gameSocket = new WebSocket(
ws_scheme +
'://'
+ window.location.host
+ '/ws/play/'
+ game_id
+ '/'
)
let vue = new Vue({
el: '#app',
data: {
current_turn: 0,
last_turn: -1,
current_card: 0,
last_card: -1,
number_of_stacked_cards: 0,
last_amount_played: 0,
won_by: -1,
my_cards: [],
other_players_data: {},
},
created() {
gameSocket.onmessage = function(e) {
data = JSON.parse(e.data)
this.current_turn = data.state.current_turn
this.last_turn = data.state.last_turn
// ... update the other data
};
},
});
When I receive the message, logging the data makes it apparent that I'm receiving correct information. However, if I go and type vue.current_turn
after receiving the message, it's still 0
instead of the new value; same for all the other members of the data
object.
I tried with vue.current_turn = data.state.current_turn
and it does work this way, but obviously it should work with this
.
What's wrong with my code?
And generally speaking, what's the best way of acplishing what I'm after, i.e. updating internal data variables upon receiving messages from a socket?
I have to do with without using the socket.io library, which isn't supported by channels.
Share Improve this question edited Sep 20, 2020 at 17:18 Adam Zerner 19.4k18 gold badges101 silver badges175 bronze badges asked Sep 20, 2020 at 16:35 Samuele B.Samuele B. 6581 gold badge12 silver badges42 bronze badges1 Answer
Reset to default 8The issue is that this
is pointing to whatever calls gameSocket.onmessage
, not the "normal Vue this
".
To get around the issue you could do let self = this
above gameSocket.onmessage
and use self
inside of it.