Compare commits
14 Commits
6ee7a435e0
...
main
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
d4a7b41d70 | ||
|
|
ce5b660350 | ||
|
|
eecc9becbc | ||
|
|
752061f92f | ||
|
|
e786d42e98 | ||
|
|
ab13de5bc3 | ||
|
|
a9d6476b75 | ||
|
|
b269656833 | ||
|
|
d48ff10b2f | ||
|
|
8c0d13d096 | ||
|
|
1bc950d97b | ||
|
|
890faab9fc | ||
|
|
ded7da8e73 | ||
|
|
694ccc14a4 |
60
app.py
60
app.py
@@ -209,12 +209,12 @@ favicon_update = Path("favicon_update.ico").read_bytes()
|
||||
|
||||
@app.GET("/favicon.ico")
|
||||
async def favicon_s(request):
|
||||
return HTTPResponse(request, favicon, content_type="image/x-icon")
|
||||
return HTTPResponse(favicon, content_type="image/x-icon")
|
||||
|
||||
|
||||
@app.GET("/favicon_update.ico")
|
||||
async def favicon_update_s(request):
|
||||
return HTTPResponse(request, favicon_update, content_type="image/x-icon")
|
||||
return HTTPResponse(favicon_update, content_type="image/x-icon")
|
||||
|
||||
|
||||
letters = string.ascii_lowercase + string.digits
|
||||
@@ -234,21 +234,21 @@ async def new_room(request):
|
||||
key = room_key()
|
||||
rooms[key] = Room()
|
||||
return JSONResponse(
|
||||
request,
|
||||
{
|
||||
"id": key,
|
||||
},
|
||||
)
|
||||
|
||||
|
||||
quick_queue: deque[str]
|
||||
quick_map: dict[str, Room]
|
||||
quick_queue: deque[str] = deque()
|
||||
quick_map: dict[str, Room] = {}
|
||||
quick_last_map: dict[str, datetime] = {}
|
||||
lock = asyncio.Lock()
|
||||
|
||||
|
||||
@app.POST("/quick")
|
||||
async def quick_match(request: Request):
|
||||
global quick_queue, quick_map
|
||||
global quick_queue, quick_map, quick_last_map
|
||||
data = parse(request.body)
|
||||
async with lock:
|
||||
if (
|
||||
@@ -261,6 +261,13 @@ async def quick_match(request: Request):
|
||||
second = None
|
||||
position: int = 0
|
||||
# UPDATE LOGIC
|
||||
now = datetime.now(timezone.utc)
|
||||
for q, t in quick_last_map.items():
|
||||
if t - now >= timedelta(seconds=3):
|
||||
quick_queue.remove(q)
|
||||
del quick_map[q]
|
||||
del quick_last_map[q]
|
||||
|
||||
while position < len(quick_queue):
|
||||
if quick_queue[position] not in quick_map:
|
||||
if not first:
|
||||
@@ -273,18 +280,27 @@ async def quick_match(request: Request):
|
||||
room = Room()
|
||||
k = room_key()
|
||||
rooms[k] = room
|
||||
quick_map[first] = room
|
||||
quick_map[second] = room
|
||||
quick_map[first] = k
|
||||
quick_map[second] = k
|
||||
|
||||
qid = data["queue_id"]
|
||||
quick_last_map[qid] = datetime.now(timezone.utc)
|
||||
if qid in quick_map:
|
||||
return JSONResponse({"room_id": quick_map[qid]})
|
||||
else:
|
||||
return JSONResponse({}) # Client handles empty as continue to wait
|
||||
|
||||
elif (
|
||||
data
|
||||
and len(data) == 2
|
||||
and "queue_id" in data
|
||||
and data["queue_id"] in quick_queue
|
||||
and "leave" in data
|
||||
):
|
||||
quick_queue.remove(data["queue_id"])
|
||||
else:
|
||||
qid = str(uuid.uuid4())
|
||||
quick_queue.append(qid)
|
||||
quick_last_map[qid] = datetime.now(timezone.utc)
|
||||
return JSONResponse({"queue_id": qid})
|
||||
|
||||
|
||||
@@ -310,7 +326,6 @@ async def join(request, room_id):
|
||||
player = room.add_player()
|
||||
if player:
|
||||
return JSONResponse(
|
||||
request,
|
||||
{
|
||||
"code": "JOIN",
|
||||
"id": player[0],
|
||||
@@ -326,7 +341,6 @@ async def join(request, room_id):
|
||||
)
|
||||
else:
|
||||
return JSONResponse(
|
||||
request,
|
||||
{
|
||||
"code": "FULL",
|
||||
"error": "Room Full",
|
||||
@@ -358,14 +372,12 @@ def get_piece_moves(piece_kind, board: Board, is_white, src: str) -> list[Coord]
|
||||
if (y == 1 or y == 6) and board.index_xy(x, y + 2 * dir) == Piece.EMPTY:
|
||||
valids.append(Coord(x=x, y=y + 2 * dir))
|
||||
if (
|
||||
board.index_xy(x + 1, y + dir)
|
||||
not in [Piece.EMPTY, Piece.NONE, Piece.BLACK_KING, Piece.WHITE_KING]
|
||||
board.index_xy(x + 1, y + dir) not in [Piece.EMPTY, Piece.NONE]
|
||||
and board.index_xy(x + 1, y + dir).value.isupper() != is_white
|
||||
):
|
||||
valids.append(Coord(x=x + 1, y=y + dir))
|
||||
if (
|
||||
board.index_xy(x - 1, y + dir)
|
||||
not in [Piece.EMPTY, Piece.NONE, Piece.BLACK_KING, Piece.WHITE_KING]
|
||||
board.index_xy(x - 1, y + dir) not in [Piece.EMPTY, Piece.NONE]
|
||||
and board.index_xy(x - 1, y + dir).value.isupper() != is_white
|
||||
):
|
||||
valids.append(Coord(x=x - 1, y=y + dir))
|
||||
@@ -462,7 +474,6 @@ def generate_valid_moves(
|
||||
):
|
||||
king = Coord(j, i)
|
||||
break
|
||||
|
||||
for m in possible_moves:
|
||||
fake_board = board.copy()
|
||||
fake_board.grid[m.y][m.x] = fake_board.index(src)
|
||||
@@ -471,24 +482,13 @@ def generate_valid_moves(
|
||||
king_safe = True
|
||||
for i in range(8):
|
||||
for j in range(8):
|
||||
p = board.grid[j][i]
|
||||
p = board.index_xy(j, i)
|
||||
if p != Piece.EMPTY and p.value.isupper() != is_white:
|
||||
# Enemy
|
||||
enemy_moves = get_piece_moves(
|
||||
p.value.lower(), board, not is_white, xy_to_pos_safe(j, i)
|
||||
)
|
||||
if king not in enemy_moves:
|
||||
continue
|
||||
ni = i
|
||||
nj = j
|
||||
if j == sx and i == sy:
|
||||
ni = m.y
|
||||
nj = m.x
|
||||
new_enemy_moves = get_piece_moves(
|
||||
p.value.lower(),
|
||||
fake_board,
|
||||
not is_white,
|
||||
xy_to_pos_safe(nj, ni),
|
||||
xy_to_pos_safe(j, i),
|
||||
)
|
||||
if king in new_enemy_moves:
|
||||
king_safe = False
|
||||
@@ -573,7 +573,7 @@ async def move(request: Request, room_id):
|
||||
if not opp_checkmate:
|
||||
break
|
||||
if opp_checkmate:
|
||||
room.state = State.BLACK_WIN if is_white else State.WHITE_WIN
|
||||
room.state = State.WHITE_WIN if is_white else State.BLACK_WIN
|
||||
return {
|
||||
"code": "MOVD",
|
||||
"color": color.value,
|
||||
|
||||
@@ -141,11 +141,12 @@
|
||||
const textures = {};
|
||||
|
||||
const piecemoveSound = new Audio("/static/piecemove.mp3");
|
||||
//const endgameSound = new Audio("/static/endgame.mp3");
|
||||
const endgameSound = new Audio("/static/endgame.mp3");
|
||||
|
||||
let color = 0;
|
||||
let turn = 0;
|
||||
let state = -1;
|
||||
let oldState = -1;
|
||||
let start_time = undefined;
|
||||
let ready = false;
|
||||
let letterMap = ' ';
|
||||
@@ -187,7 +188,11 @@
|
||||
.catch(error => {
|
||||
console.error("Playback failed:", error);
|
||||
});
|
||||
if (oldState !== state && state >= 1) {
|
||||
endgameSound.play();
|
||||
}
|
||||
oldBoard = structuredClone(board);
|
||||
oldState = state;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -326,9 +331,9 @@
|
||||
ready = data.ready;
|
||||
turn = data.turn;
|
||||
board = data.board.grid;
|
||||
boardOnChange();
|
||||
state = data.state;
|
||||
start_time = new Date(data.start_time);
|
||||
boardOnChange();
|
||||
|
||||
setUI();
|
||||
})
|
||||
|
||||
76
home.html
76
home.html
@@ -70,7 +70,6 @@
|
||||
.code {
|
||||
padding: 16px;
|
||||
border: none;
|
||||
border-bottom: 2px solid rgba(92, 92, 92, 0.664);
|
||||
font-size: 1.5rem;
|
||||
text-align: center;
|
||||
letter-spacing: 8px;
|
||||
@@ -94,19 +93,18 @@
|
||||
|
||||
.group {
|
||||
display: flex;
|
||||
height: 60px;
|
||||
gap: 4px;
|
||||
height: 48px;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.group * {
|
||||
height: 60px;
|
||||
height: 48px;
|
||||
margin-bottom: 4px;
|
||||
}
|
||||
|
||||
.vs {
|
||||
height: calc(100% - 8px);
|
||||
width: 2px;
|
||||
margin: 4px;
|
||||
background: rgba(92, 92, 92, 0.664);
|
||||
}
|
||||
|
||||
@@ -126,6 +124,13 @@
|
||||
background-repeat: no-repeat;
|
||||
|
||||
}
|
||||
|
||||
#quick_match_info {
|
||||
margin: 14px 0;
|
||||
font-size: 18px;
|
||||
user-select: none;
|
||||
color: rgba(92, 92, 92, 0.664);
|
||||
}
|
||||
</style>
|
||||
<link rel="icon" href="/favicon.ico" type="image/x-icon">
|
||||
</head>
|
||||
@@ -145,19 +150,74 @@
|
||||
<button id="join" class="button">join</button>
|
||||
</div>
|
||||
<div class="or"></div>
|
||||
Public games not added yet.
|
||||
<div id="quick_match_info" style="visibility: hidden;">Searching for a game</div>
|
||||
<button class="button" id="quick_match">quick match</button>
|
||||
</div>
|
||||
|
||||
<script>
|
||||
|
||||
let dots = 0;
|
||||
|
||||
setInterval(() => {
|
||||
let text = "Searching for a game";
|
||||
for (let i = 0; i < dots; i++) {
|
||||
text += ".";
|
||||
}
|
||||
document.getElementById("quick_match_info").innerText = text;
|
||||
dots += 1;
|
||||
if (dots == 4) {
|
||||
dots = 0;
|
||||
}
|
||||
}, 1000);
|
||||
|
||||
document.addEventListener('DOMContentLoaded', () => {
|
||||
const code = document.getElementById("code");
|
||||
const pat = new RegExp("^[a-z0-9]{4}$")
|
||||
document.getElementById("join").addEventListener("click", () => {
|
||||
if (!reg.test(code.value)) {
|
||||
if (!pat.test(code.value.toLowerCase())) {
|
||||
alert("Invalid ID");
|
||||
} else {
|
||||
window.location.href = window.location.origin + "/" + code.value;
|
||||
window.location.href = window.location.origin + "/" + code.value.toLowerCase();
|
||||
}
|
||||
});
|
||||
const qm = document.getElementById("quick_match");
|
||||
let matchmaking = -1;
|
||||
let qid = -1;
|
||||
qm.addEventListener("click", () => {
|
||||
if (qm.innerText.toLowerCase() === "cancel") {
|
||||
qm.innerText = "quick match";
|
||||
document.getElementById("quick_match_info").style.visibility = "hidden";
|
||||
clearInterval(-1);
|
||||
} else if (qm.innerText.toLowerCase() === "quick match") {
|
||||
qm.innerText = "cancel";
|
||||
document.getElementById("quick_match_info").style.visibility = "visible";
|
||||
fetch("/quick", {
|
||||
method: 'POST',
|
||||
})
|
||||
.then((response) => response.json())
|
||||
.then((data) => {
|
||||
qid = data.queue_id;
|
||||
matchmaking = setInterval(() => {
|
||||
fetch("/quick", {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
body: JSON.stringify({ "queue_id": qid }),
|
||||
})
|
||||
.then((response) => response.json())
|
||||
.then((data) => {
|
||||
if (data.room_id) {
|
||||
clearInterval(matchmaking);
|
||||
window.location.href = window.location.origin + "/" + data.room_id;
|
||||
}
|
||||
}).catch((error) => {
|
||||
console.error(error);
|
||||
})
|
||||
}, 1500);
|
||||
}).catch((error) => {
|
||||
console.error(error);
|
||||
})
|
||||
}
|
||||
});
|
||||
document.getElementById("create").addEventListener("click", () => {
|
||||
|
||||
2
libs
2
libs
Submodule libs updated: fe65fafbe0...c455adea07
Reference in New Issue
Block a user