Files
SansanandClaude Opus 5.5 83ff9511ec Save best scores and last difficulty to a JSON profile
- profile package: best moves, best time and games played per
  deck/difficulty, stored in the user data folder
- Win panel shows the best (or New best!), language menu shows bests
- Profile memory always comes from the heap allocator (it outlives callers)

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-01 21:35:43 +02:00

71 lines
2.4 KiB
Odin

package tests
import "core:os"
import "core:testing"
import memory "../src/memory"
import profile "../src/profile"
@(test)
record_game_tracks_bests :: proc(t: ^testing.T) {
key := "TEST/RECORD"
first := profile.record_game(key, 20, 90)
testing.expect_value(t, first.record.games, 1)
testing.expect_value(t, first.record.best_moves, 20)
testing.expect(t, !first.new_best_moves && !first.new_best_time) // nothing to beat yet
worse := profile.record_game(key, 25, 120)
testing.expect(t, !worse.new_best_moves && !worse.new_best_time)
testing.expect_value(t, worse.record.best_moves, 20)
// Fewer moves but slower: only the moves record changes
fewer := profile.record_game(key, 15, 100)
testing.expect(t, fewer.new_best_moves && !fewer.new_best_time)
testing.expect_value(t, fewer.record.best_moves, 15)
testing.expect_value(t, fewer.record.best_seconds, 90)
testing.expect_value(t, fewer.record.games, 3)
}
@(test)
profile_round_trips_through_json :: proc(t: ^testing.T) {
path := "build/test-profile.json"
os.remove(path)
defer os.remove(path)
testing.expect(t, profile.init(path))
defer profile.path = "" // stop other tests from writing the file
profile.set_difficulty("HARD")
profile.record_game("TEST/SAVE", 12, 61.5)
// Reload from disk into a clean state
profile.data = {}
testing.expect(t, profile.init(path))
testing.expect_value(t, profile.data.difficulty, "HARD")
record, ok := profile.get("TEST/SAVE")
testing.expect(t, ok)
testing.expect_value(t, record.best_moves, 12)
testing.expect_value(t, record.best_seconds, 61.5)
}
@(test)
winning_records_a_score :: proc(t: ^testing.T) {
memory.deal(.KATAKANA, .EASY)
for i in 0 ..< memory.card_count {
if memory.cards[i].matched { continue }
memory.select_card(i)
memory.select_card(partner_of(i))
advance(2)
}
testing.expect_value(t, memory.state, memory.State.OVER)
record, ok := profile.get(memory.score_key(.KATAKANA, .EASY))
testing.expect(t, ok)
testing.expect_value(t, record.best_moves, memory.pair_count)
testing.expect_value(t, memory.last_result.record.games, record.games)
}
@(test)
time_format :: proc(t: ^testing.T) {
testing.expect_value(t, profile.format_time(0), "0:00")
testing.expect_value(t, profile.format_time(65.9), "1:05")
testing.expect_value(t, profile.format_time(600), "10:00")
}