Add game end condition check and simple scoring end screen
This commit is contained in:
		
							
								
								
									
										16
									
								
								Cargo.lock
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										16
									
								
								Cargo.lock
									
									
									
										generated
									
									
									
								
							@@ -580,6 +580,7 @@ version = "0.1.0"
 | 
				
			|||||||
dependencies = [
 | 
					dependencies = [
 | 
				
			||||||
 "async-std",
 | 
					 "async-std",
 | 
				
			||||||
 "html-escape",
 | 
					 "html-escape",
 | 
				
			||||||
 | 
					 "itertools",
 | 
				
			||||||
 "rand 0.8.0",
 | 
					 "rand 0.8.0",
 | 
				
			||||||
 "serde",
 | 
					 "serde",
 | 
				
			||||||
 "serde_json",
 | 
					 "serde_json",
 | 
				
			||||||
@@ -588,6 +589,12 @@ dependencies = [
 | 
				
			|||||||
 "uuid",
 | 
					 "uuid",
 | 
				
			||||||
]
 | 
					]
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					[[package]]
 | 
				
			||||||
 | 
					name = "either"
 | 
				
			||||||
 | 
					version = "1.6.1"
 | 
				
			||||||
 | 
					source = "registry+https://github.com/rust-lang/crates.io-index"
 | 
				
			||||||
 | 
					checksum = "e78d4f1cc4ae33bbfc157ed5d5a5ef3bc29227303d595861deb238fcec4e9457"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
[[package]]
 | 
					[[package]]
 | 
				
			||||||
name = "event-listener"
 | 
					name = "event-listener"
 | 
				
			||||||
version = "2.5.1"
 | 
					version = "2.5.1"
 | 
				
			||||||
@@ -902,6 +909,15 @@ dependencies = [
 | 
				
			|||||||
 "cfg-if 1.0.0",
 | 
					 "cfg-if 1.0.0",
 | 
				
			||||||
]
 | 
					]
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					[[package]]
 | 
				
			||||||
 | 
					name = "itertools"
 | 
				
			||||||
 | 
					version = "0.10.0"
 | 
				
			||||||
 | 
					source = "registry+https://github.com/rust-lang/crates.io-index"
 | 
				
			||||||
 | 
					checksum = "37d572918e350e82412fe766d24b15e6682fb2ed2bbe018280caa810397cb319"
 | 
				
			||||||
 | 
					dependencies = [
 | 
				
			||||||
 | 
					 "either",
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					
 | 
				
			||||||
[[package]]
 | 
					[[package]]
 | 
				
			||||||
name = "itoa"
 | 
					name = "itoa"
 | 
				
			||||||
version = "0.4.6"
 | 
					version = "0.4.6"
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -9,6 +9,7 @@ edition = "2018"
 | 
				
			|||||||
[dependencies]
 | 
					[dependencies]
 | 
				
			||||||
async-std = { version = "1.8.0", features = ["attributes"] }
 | 
					async-std = { version = "1.8.0", features = ["attributes"] }
 | 
				
			||||||
html-escape = "0.2.6"
 | 
					html-escape = "0.2.6"
 | 
				
			||||||
 | 
					itertools = "0.10.0"
 | 
				
			||||||
rand = "0.8.0"
 | 
					rand = "0.8.0"
 | 
				
			||||||
serde = { version = "1.0", features = ["derive"] }
 | 
					serde = { version = "1.0", features = ["derive"] }
 | 
				
			||||||
serde_json = "1.0.60" 
 | 
					serde_json = "1.0.60" 
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										45
									
								
								src/main.rs
									
									
									
									
									
								
							
							
						
						
									
										45
									
								
								src/main.rs
									
									
									
									
									
								
							@@ -1,4 +1,5 @@
 | 
				
			|||||||
use async_std::{prelude::*, sync::RwLock};
 | 
					use async_std::{prelude::*, sync::RwLock};
 | 
				
			||||||
 | 
					use itertools::Itertools;
 | 
				
			||||||
use rand::{seq::SliceRandom, thread_rng};
 | 
					use rand::{seq::SliceRandom, thread_rng};
 | 
				
			||||||
use serde::{Deserialize, Serialize};
 | 
					use serde::{Deserialize, Serialize};
 | 
				
			||||||
use std::{collections::HashMap, sync::Arc};
 | 
					use std::{collections::HashMap, sync::Arc};
 | 
				
			||||||
@@ -53,6 +54,9 @@ enum ServerMessage {
 | 
				
			|||||||
    Notification {
 | 
					    Notification {
 | 
				
			||||||
        text: String,
 | 
					        text: String,
 | 
				
			||||||
    },
 | 
					    },
 | 
				
			||||||
 | 
					    GameOver {
 | 
				
			||||||
 | 
					        score: Vec<(usize, usize)>,
 | 
				
			||||||
 | 
					    },
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#[derive(Clone, Serialize)]
 | 
					#[derive(Clone, Serialize)]
 | 
				
			||||||
@@ -130,6 +134,7 @@ impl Player {
 | 
				
			|||||||
enum GameState {
 | 
					enum GameState {
 | 
				
			||||||
    Setup,
 | 
					    Setup,
 | 
				
			||||||
    InProgress,
 | 
					    InProgress,
 | 
				
			||||||
 | 
					    Over,
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
impl Default for GameSetup {
 | 
					impl Default for GameSetup {
 | 
				
			||||||
@@ -219,10 +224,29 @@ impl Game {
 | 
				
			|||||||
            }
 | 
					            }
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        self.end_game();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        self.active_player += 1;
 | 
					        self.active_player += 1;
 | 
				
			||||||
        self.active_player %= self.players.len();
 | 
					        self.active_player %= self.players.len();
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    // Check if the end game condition is reached and finish the game if so,
 | 
				
			||||||
 | 
					    // sending a message to all clients.
 | 
				
			||||||
 | 
					    fn end_game(&mut self) {
 | 
				
			||||||
 | 
					        let provinces = self.supply.iter().any(|(c, n)| *c == "Province" && *n == 0);
 | 
				
			||||||
 | 
					        let supply = self.supply.iter().filter(|(_, n)| *n == 0).count() > 2;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        if supply || provinces {
 | 
				
			||||||
 | 
					            self.state = GameState::Over;
 | 
				
			||||||
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        for p in self.players.iter_mut() {
 | 
				
			||||||
 | 
					            p.draw_pile.append(&mut p.played_cards);
 | 
				
			||||||
 | 
					            p.draw_pile.append(&mut p.hand);
 | 
				
			||||||
 | 
					            p.draw_pile.append(&mut p.discard_pile);
 | 
				
			||||||
 | 
					        }
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    fn is_active_player(&self, player_id: &str) -> bool {
 | 
					    fn is_active_player(&self, player_id: &str) -> bool {
 | 
				
			||||||
        match self.players.get(self.active_player) {
 | 
					        match self.players.get(self.active_player) {
 | 
				
			||||||
            None => false,
 | 
					            None => false,
 | 
				
			||||||
@@ -294,6 +318,27 @@ async fn broadcast_state(game: &Game) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
        send_msg(&game, &p, &sm).await;
 | 
					        send_msg(&game, &p, &sm).await;
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    if game.state == GameState::Over {
 | 
				
			||||||
 | 
					        let sm = ServerMessage::GameOver {
 | 
				
			||||||
 | 
					            score: game
 | 
				
			||||||
 | 
					                .players
 | 
				
			||||||
 | 
					                .iter()
 | 
				
			||||||
 | 
					                .enumerate()
 | 
				
			||||||
 | 
					                .map(|(i, p)| {
 | 
				
			||||||
 | 
					                    let score = p.draw_pile.iter().fold(0, |acc, card| match card.as_str() {
 | 
				
			||||||
 | 
					                        "Province" => acc + 6,
 | 
				
			||||||
 | 
					                        "Duchery" => acc + 3,
 | 
				
			||||||
 | 
					                        "Estate" => acc + 1,
 | 
				
			||||||
 | 
					                        _ => acc,
 | 
				
			||||||
 | 
					                    });
 | 
				
			||||||
 | 
					                    (i, score)
 | 
				
			||||||
 | 
					                })
 | 
				
			||||||
 | 
					                .sorted_by(|a, b| Ord::cmp(&b.1, &a.1))
 | 
				
			||||||
 | 
					                .collect::<Vec<_>>(),
 | 
				
			||||||
 | 
					        };
 | 
				
			||||||
 | 
					        broadcast(&game, &sm).await;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
async fn send_msg(game: &Game, player: &Player, sm: &ServerMessage) {
 | 
					async fn send_msg(game: &Game, player: &Player, sm: &ServerMessage) {
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										135
									
								
								static/game.html
									
									
									
									
									
								
							
							
						
						
									
										135
									
								
								static/game.html
									
									
									
									
									
								
							@@ -8,8 +8,9 @@
 | 
				
			|||||||
<style type="text/css">
 | 
					<style type="text/css">
 | 
				
			||||||
#game {
 | 
					#game {
 | 
				
			||||||
    display: grid;
 | 
					    display: grid;
 | 
				
			||||||
    grid-template-columns: auto auto;
 | 
					    grid-template-columns: auto 300px;
 | 
				
			||||||
    user-select: none;
 | 
					    user-select: none;
 | 
				
			||||||
 | 
					    position: relative;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
.pile-counter {
 | 
					.pile-counter {
 | 
				
			||||||
@@ -53,7 +54,7 @@
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
.player-hand {
 | 
					.player-hand {
 | 
				
			||||||
    border: 1px solid red;
 | 
					    border: 1px solid red;
 | 
				
			||||||
    height: 160px;
 | 
					    height: 165px;
 | 
				
			||||||
    margin: 0;
 | 
					    margin: 0;
 | 
				
			||||||
    box-sizing: border-box;
 | 
					    box-sizing: border-box;
 | 
				
			||||||
    overflow-x: scroll;
 | 
					    overflow-x: scroll;
 | 
				
			||||||
@@ -68,6 +69,8 @@
 | 
				
			|||||||
    border: 1px solid black;
 | 
					    border: 1px solid black;
 | 
				
			||||||
    width: 300px;
 | 
					    width: 300px;
 | 
				
			||||||
    grid-column-start: 2;
 | 
					    grid-column-start: 2;
 | 
				
			||||||
 | 
					    grid-row-start: 1;
 | 
				
			||||||
 | 
					    box-sizing: border-box;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#chat li[data-repeat]::after {
 | 
					#chat li[data-repeat]::after {
 | 
				
			||||||
@@ -109,7 +112,7 @@
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
.supply-pile::after {
 | 
					.supply-pile::after {
 | 
				
			||||||
    position: absolute;
 | 
					    position: absolute;
 | 
				
			||||||
    bottom: 5px;
 | 
					    bottom: 20px;
 | 
				
			||||||
    right: 5px;
 | 
					    right: 5px;
 | 
				
			||||||
    color: wheat;
 | 
					    color: wheat;
 | 
				
			||||||
    background-color: darkred;
 | 
					    background-color: darkred;
 | 
				
			||||||
@@ -211,6 +214,10 @@
 | 
				
			|||||||
    padding-top: 0;
 | 
					    padding-top: 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					.inplay-area img.card {
 | 
				
			||||||
 | 
					    margin-left: -55px;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
.turn-status {
 | 
					.turn-status {
 | 
				
			||||||
    line-height: 24px;
 | 
					    line-height: 24px;
 | 
				
			||||||
    height: 24px;
 | 
					    height: 24px;
 | 
				
			||||||
@@ -309,6 +316,57 @@
 | 
				
			|||||||
    z-index: -1;
 | 
					    z-index: -1;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					 #preview {
 | 
				
			||||||
 | 
					    grid-column-start: 2;
 | 
				
			||||||
 | 
					    grid-row-start: 1;
 | 
				
			||||||
 | 
					    height: 290px;
 | 
				
			||||||
 | 
					    margin-top: 500px;
 | 
				
			||||||
 | 
					 }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#preview img {
 | 
				
			||||||
 | 
					    height: 290px;
 | 
				
			||||||
 | 
					    width: 180px;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#modal {
 | 
				
			||||||
 | 
					    display: none;
 | 
				
			||||||
 | 
					    grid-row-start: 1;
 | 
				
			||||||
 | 
					    grid-column-end: 2;
 | 
				
			||||||
 | 
					    position: absolute;
 | 
				
			||||||
 | 
					    top: 0;
 | 
				
			||||||
 | 
					    left: 0;
 | 
				
			||||||
 | 
					    width: 100%;
 | 
				
			||||||
 | 
					    height: 100%;
 | 
				
			||||||
 | 
					    background-color: rgba(1.0, 1.0, 1.0, 0.6);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					.modal-content {
 | 
				
			||||||
 | 
					    width: 600px;
 | 
				
			||||||
 | 
					    height: 300px;
 | 
				
			||||||
 | 
					    position: relative;
 | 
				
			||||||
 | 
					    top: 50%;
 | 
				
			||||||
 | 
					    left: 50%;
 | 
				
			||||||
 | 
					    transform: translate(-50%, -50%);
 | 
				
			||||||
 | 
					    background-color: lightgray;
 | 
				
			||||||
 | 
					    box-shadow: 0 0 10px;
 | 
				
			||||||
 | 
					    border: 1px solid black;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					.modal-content h1 {
 | 
				
			||||||
 | 
					    text-align: center;
 | 
				
			||||||
 | 
					    margin-top: 1px;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					.rank {
 | 
				
			||||||
 | 
					    display: flex;
 | 
				
			||||||
 | 
					    border-bottom: 1px solid dimgray;
 | 
				
			||||||
 | 
					    padding: 2px;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					.rank span:first-child {
 | 
				
			||||||
 | 
					    width: 120px;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
</style>
 | 
					</style>
 | 
				
			||||||
<script src="/static/mithril.js"></script>
 | 
					<script src="/static/mithril.js"></script>
 | 
				
			||||||
</head>
 | 
					</head>
 | 
				
			||||||
@@ -316,7 +374,17 @@
 | 
				
			|||||||
<body>
 | 
					<body>
 | 
				
			||||||
    <div id="game"></div>
 | 
					    <div id="game"></div>
 | 
				
			||||||
    <script>
 | 
					    <script>
 | 
				
			||||||
        function handle_dnd(data) {
 | 
					         var mouseenter = function(ev) {
 | 
				
			||||||
 | 
					             var img = ev.target.src;
 | 
				
			||||||
 | 
					             document.querySelector("#preview img").src = img;
 | 
				
			||||||
 | 
					             document.querySelector("#preview img").style.visibility = "visible";
 | 
				
			||||||
 | 
					         }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					         var mouseleave = function(ev) {
 | 
				
			||||||
 | 
					             document.querySelector("#preview img").style.visibility = "hidden";
 | 
				
			||||||
 | 
					         }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					         function handle_dnd(data) {
 | 
				
			||||||
            if (data.source == "Hand" && data.dest == "InPlay") {
 | 
					            if (data.source == "Hand" && data.dest == "InPlay") {
 | 
				
			||||||
                var msg = { type: "PlayCard", name: "", index: data.index};
 | 
					                var msg = { type: "PlayCard", name: "", index: data.index};
 | 
				
			||||||
                webSocket.send(JSON.stringify(msg));
 | 
					                webSocket.send(JSON.stringify(msg));
 | 
				
			||||||
@@ -348,7 +416,7 @@
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
            return {
 | 
					            return {
 | 
				
			||||||
                view: function(vnode) {
 | 
					                view: function(vnode) {
 | 
				
			||||||
                    return m(".chat-window",
 | 
					                    return [m(".chat-window",
 | 
				
			||||||
                        m("h4", "Players"),
 | 
					                        m("h4", "Players"),
 | 
				
			||||||
                        m("ul", vnode.attrs.players.map(function(p) {
 | 
					                        m("ul", vnode.attrs.players.map(function(p) {
 | 
				
			||||||
                            return m("li", p.name);
 | 
					                            return m("li", p.name);
 | 
				
			||||||
@@ -359,8 +427,10 @@
 | 
				
			|||||||
                            id: "chat_input",
 | 
					                            id: "chat_input",
 | 
				
			||||||
                            placeholder: "Type to chat...",
 | 
					                            placeholder: "Type to chat...",
 | 
				
			||||||
                            onkeyup: keyup
 | 
					                            onkeyup: keyup
 | 
				
			||||||
                        })
 | 
					                        }),
 | 
				
			||||||
                    )
 | 
					                    ),
 | 
				
			||||||
 | 
					                    m("#preview", m("img")),
 | 
				
			||||||
 | 
					                    ]
 | 
				
			||||||
                }
 | 
					                }
 | 
				
			||||||
            }
 | 
					            }
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
@@ -376,7 +446,7 @@
 | 
				
			|||||||
                ev.dataTransfer.setData("text", JSON.stringify(data));
 | 
					                ev.dataTransfer.setData("text", JSON.stringify(data));
 | 
				
			||||||
            }
 | 
					            }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
            return {
 | 
					           return {
 | 
				
			||||||
                view: function(vnode) {
 | 
					                view: function(vnode) {
 | 
				
			||||||
                    return m(".supply-pile",
 | 
					                    return m(".supply-pile",
 | 
				
			||||||
                        {
 | 
					                        {
 | 
				
			||||||
@@ -390,6 +460,8 @@
 | 
				
			|||||||
                            class: "card",
 | 
					                            class: "card",
 | 
				
			||||||
                            src: "/static/images/cards/" + vnode.attrs.name.toLowerCase() + ".jpg",
 | 
					                            src: "/static/images/cards/" + vnode.attrs.name.toLowerCase() + ".jpg",
 | 
				
			||||||
                            draggable: false,
 | 
					                            draggable: false,
 | 
				
			||||||
 | 
					                            onmouseenter: mouseenter,
 | 
				
			||||||
 | 
					                            onmouseleave: mouseleave,
 | 
				
			||||||
                        })
 | 
					                        })
 | 
				
			||||||
                    )
 | 
					                    )
 | 
				
			||||||
                }
 | 
					                }
 | 
				
			||||||
@@ -693,19 +765,34 @@
 | 
				
			|||||||
                        m("h4", "Basic cards"),
 | 
					                        m("h4", "Basic cards"),
 | 
				
			||||||
                        m(".basic-cards",
 | 
					                        m(".basic-cards",
 | 
				
			||||||
                            vnode.attrs.basic_cards.map(function(card) {
 | 
					                            vnode.attrs.basic_cards.map(function(card) {
 | 
				
			||||||
                                return m("img", {class: "card", src: "/static/images/cards/" + card.toLowerCase() + ".jpg"})
 | 
					                                return m("img", {
 | 
				
			||||||
 | 
					                                    class: "card",
 | 
				
			||||||
 | 
					                                    src: "/static/images/cards/" + card.toLowerCase() + ".jpg",
 | 
				
			||||||
 | 
					                                    onmouseenter: mouseenter,
 | 
				
			||||||
 | 
					                                    onmouseleave: mouseleave,
 | 
				
			||||||
 | 
					                                })
 | 
				
			||||||
                            })
 | 
					                            })
 | 
				
			||||||
                        ),
 | 
					                        ),
 | 
				
			||||||
                        m("h4", "Kingdom Cards"),
 | 
					                        m("h4", "Kingdom Cards"),
 | 
				
			||||||
                        m(".kingdom-cards",
 | 
					                        m(".kingdom-cards",
 | 
				
			||||||
                            vnode.attrs.kingdom_cards.map(function(card) {
 | 
					                            vnode.attrs.kingdom_cards.map(function(card) {
 | 
				
			||||||
                                return m("img", {class: "card", src: "/static/images/cards/" + card.toLowerCase() + ".jpg"})
 | 
					                                return m("img", {
 | 
				
			||||||
 | 
					                                    class: "card",
 | 
				
			||||||
 | 
					                                    src: "/static/images/cards/" + card.toLowerCase() + ".jpg",
 | 
				
			||||||
 | 
					                                    onmouseenter: mouseenter,
 | 
				
			||||||
 | 
					                                    onmouseleave: mouseleave,
 | 
				
			||||||
 | 
					                                })
 | 
				
			||||||
                            })
 | 
					                            })
 | 
				
			||||||
                        ),
 | 
					                        ),
 | 
				
			||||||
                        m("h4", "Starting Deck"),
 | 
					                        m("h4", "Starting Deck"),
 | 
				
			||||||
                        m(".start-deck",
 | 
					                        m(".start-deck",
 | 
				
			||||||
                            vnode.attrs.starting_deck.map(function(card) {
 | 
					                            vnode.attrs.starting_deck.map(function(card) {
 | 
				
			||||||
                                return m("img", {class: "card", src: "/static/images/cards/" + card.toLowerCase() + ".jpg"})
 | 
					                                return m("img", {
 | 
				
			||||||
 | 
					                                    class: "card",
 | 
				
			||||||
 | 
					                                    src: "/static/images/cards/" + card.toLowerCase() + ".jpg",
 | 
				
			||||||
 | 
					                                    onmouseenter: mouseenter,
 | 
				
			||||||
 | 
					                                    onmouseleave: mouseleave,
 | 
				
			||||||
 | 
					                                })
 | 
				
			||||||
                            })
 | 
					                            })
 | 
				
			||||||
                        ),
 | 
					                        ),
 | 
				
			||||||
                        m("button", {onclick: start_click}, "Start Game")
 | 
					                        m("button", {onclick: start_click}, "Start Game")
 | 
				
			||||||
@@ -714,10 +801,27 @@
 | 
				
			|||||||
            }
 | 
					            }
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        function EndScreen(initialVnode) {
 | 
				
			||||||
 | 
					            return {
 | 
				
			||||||
 | 
					                view: function(vnode) {
 | 
				
			||||||
 | 
					                    return m(".modal-content",
 | 
				
			||||||
 | 
					                        m("h1", "Score"),
 | 
				
			||||||
 | 
					                        gameover_state.map(function(rank) {
 | 
				
			||||||
 | 
					                            return m(".rank",
 | 
				
			||||||
 | 
					                                m("span", game_state.players[rank[0]].name),
 | 
				
			||||||
 | 
					                                m("span", rank[1])
 | 
				
			||||||
 | 
					                            )
 | 
				
			||||||
 | 
					                        })
 | 
				
			||||||
 | 
					                    )
 | 
				
			||||||
 | 
					                }
 | 
				
			||||||
 | 
					            }
 | 
				
			||||||
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        var game_state;
 | 
					        var game_state;
 | 
				
			||||||
        var setup_state;
 | 
					        var setup_state;
 | 
				
			||||||
        var my_player_id = 0;
 | 
					        var my_player_id = 0;
 | 
				
			||||||
        var webSocket;
 | 
					        var webSocket;
 | 
				
			||||||
 | 
					        var gameover_state;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        function App(initialVnode) {
 | 
					        function App(initialVnode) {
 | 
				
			||||||
            if (document.location.protocol == "https:") {
 | 
					            if (document.location.protocol == "https:") {
 | 
				
			||||||
@@ -779,6 +883,12 @@
 | 
				
			|||||||
                }
 | 
					                }
 | 
				
			||||||
            }
 | 
					            }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					            var handle_gameover = function(msg) {
 | 
				
			||||||
 | 
					                gameover_state = msg.score;
 | 
				
			||||||
 | 
					                var modal = document.querySelector("#modal");
 | 
				
			||||||
 | 
					                modal.style.display = "block";
 | 
				
			||||||
 | 
					                m.mount(modal, EndScreen);
 | 
				
			||||||
 | 
					            }
 | 
				
			||||||
   
 | 
					   
 | 
				
			||||||
            webSocket.onopen = function(event) {
 | 
					            webSocket.onopen = function(event) {
 | 
				
			||||||
                console.log("ws open");
 | 
					                console.log("ws open");
 | 
				
			||||||
@@ -815,6 +925,8 @@
 | 
				
			|||||||
                    handle_game_state(msg);
 | 
					                    handle_game_state(msg);
 | 
				
			||||||
                } else if (msg.type == "GameSetup") {
 | 
					                } else if (msg.type == "GameSetup") {
 | 
				
			||||||
                    handle_setup(msg.setup);
 | 
					                    handle_setup(msg.setup);
 | 
				
			||||||
 | 
					                } else if (msg.type == "GameOver") {
 | 
				
			||||||
 | 
					                    handle_gameover(msg);
 | 
				
			||||||
                } else if (msg.type == "PlayerHand") {
 | 
					                } else if (msg.type == "PlayerHand") {
 | 
				
			||||||
                    game_state.player.hand = msg.hand;
 | 
					                    game_state.player.hand = msg.hand;
 | 
				
			||||||
                } else if (msg.type == "PlayerId") {
 | 
					                } else if (msg.type == "PlayerId") {
 | 
				
			||||||
@@ -832,6 +944,7 @@
 | 
				
			|||||||
                    return [
 | 
					                    return [
 | 
				
			||||||
                        m(SetupScreen, setup_state),
 | 
					                        m(SetupScreen, setup_state),
 | 
				
			||||||
                        m(GameScreen, game_state),
 | 
					                        m(GameScreen, game_state),
 | 
				
			||||||
 | 
					                        m("#modal"),
 | 
				
			||||||
                        m(Chat, chat_state)
 | 
					                        m(Chat, chat_state)
 | 
				
			||||||
                    ]
 | 
					                    ]
 | 
				
			||||||
                }
 | 
					                }
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user