yaze 0.3.2
Link to the Past ROM Editor
 
Loading...
Searching...
No Matches
tile16_proposal_generator_test.cc
Go to the documentation of this file.
1// Test suite for Tile16ProposalGenerator
2// Tests the new ParseSetAreaCommand and ParseReplaceTileCommand functionality
3
5
6#include <gmock/gmock.h>
7#include <gtest/gtest.h>
8
9#include "app/rom.h"
10#include "test/mocks/mock_rom.h"
11
12namespace yaze {
13namespace cli {
14namespace {
15
16using ::testing::_;
17using ::testing::Return;
18
19class Tile16ProposalGeneratorTest : public ::testing::Test {
20 protected:
21 void SetUp() override {
22 generator_ = std::make_unique<Tile16ProposalGenerator>();
23 }
24
25 std::unique_ptr<Tile16ProposalGenerator> generator_;
26};
27
28// ============================================================================
29// ParseSetTileCommand Tests
30// ============================================================================
31
32TEST_F(Tile16ProposalGeneratorTest, ParseSetTileCommand_ValidCommand) {
33 std::string command = "overworld set-tile --map 0 --x 10 --y 20 --tile 0x02E";
34
35 auto result = generator_->ParseSetTileCommand(command, nullptr);
36
37 ASSERT_TRUE(result.ok()) << result.status().message();
38 EXPECT_EQ(result->map_id, 0);
39 EXPECT_EQ(result->x, 10);
40 EXPECT_EQ(result->y, 20);
41 EXPECT_EQ(result->new_tile, 0x02E);
42}
43
44TEST_F(Tile16ProposalGeneratorTest, ParseSetTileCommand_InvalidFormat) {
45 std::string command = "overworld set-tile --map 0"; // Missing required args
46
47 auto result = generator_->ParseSetTileCommand(command, nullptr);
48
49 EXPECT_FALSE(result.ok());
50 EXPECT_THAT(result.status().message(),
51 ::testing::HasSubstr("Invalid command format"));
52}
53
54TEST_F(Tile16ProposalGeneratorTest, ParseSetTileCommand_WrongCommandType) {
55 std::string command = "overworld get-tile --map 0 --x 10 --y 20";
56
57 auto result = generator_->ParseSetTileCommand(command, nullptr);
58
59 EXPECT_FALSE(result.ok());
60 EXPECT_THAT(result.status().message(),
61 ::testing::HasSubstr("Not a set-tile command"));
62}
63
64// ============================================================================
65// ParseSetAreaCommand Tests
66// ============================================================================
67
68TEST_F(Tile16ProposalGeneratorTest, ParseSetAreaCommand_ValidCommand) {
69 std::string command =
70 "overworld set-area --map 0 --x 10 --y 20 --width 5 --height 3 --tile 0x02E";
71
72 auto result = generator_->ParseSetAreaCommand(command, nullptr);
73
74 ASSERT_TRUE(result.ok()) << result.status().message();
75 EXPECT_EQ(result->size(), 15); // 5 width * 3 height = 15 tiles
76
77 // Check first tile
78 EXPECT_EQ((*result)[0].map_id, 0);
79 EXPECT_EQ((*result)[0].x, 10);
80 EXPECT_EQ((*result)[0].y, 20);
81 EXPECT_EQ((*result)[0].new_tile, 0x02E);
82
83 // Check last tile
84 EXPECT_EQ((*result)[14].x, 14); // 10 + 4
85 EXPECT_EQ((*result)[14].y, 22); // 20 + 2
86}
87
88TEST_F(Tile16ProposalGeneratorTest, ParseSetAreaCommand_SingleTile) {
89 std::string command =
90 "overworld set-area --map 0 --x 10 --y 20 --width 1 --height 1 --tile 0x02E";
91
92 auto result = generator_->ParseSetAreaCommand(command, nullptr);
93
94 ASSERT_TRUE(result.ok());
95 EXPECT_EQ(result->size(), 1);
96}
97
98TEST_F(Tile16ProposalGeneratorTest, ParseSetAreaCommand_LargeArea) {
99 std::string command =
100 "overworld set-area --map 0 --x 0 --y 0 --width 32 --height 32 --tile 0x000";
101
102 auto result = generator_->ParseSetAreaCommand(command, nullptr);
103
104 ASSERT_TRUE(result.ok());
105 EXPECT_EQ(result->size(), 1024); // 32 * 32
106}
107
108TEST_F(Tile16ProposalGeneratorTest, ParseSetAreaCommand_InvalidFormat) {
109 std::string command = "overworld set-area --map 0 --x 10"; // Missing args
110
111 auto result = generator_->ParseSetAreaCommand(command, nullptr);
112
113 EXPECT_FALSE(result.ok());
114 EXPECT_THAT(result.status().message(),
115 ::testing::HasSubstr("Invalid set-area command format"));
116}
117
118// ============================================================================
119// ParseReplaceTileCommand Tests
120// ============================================================================
121
122TEST_F(Tile16ProposalGeneratorTest, ParseReplaceTileCommand_NoROM) {
123 std::string command =
124 "overworld replace-tile --map 0 --old-tile 0x02E --new-tile 0x030";
125
126 auto result = generator_->ParseReplaceTileCommand(command, nullptr);
127
128 EXPECT_FALSE(result.ok());
129 EXPECT_THAT(result.status().message(),
130 ::testing::HasSubstr("ROM must be loaded"));
131}
132
133TEST_F(Tile16ProposalGeneratorTest, ParseReplaceTileCommand_InvalidFormat) {
134 std::string command = "overworld replace-tile --map 0"; // Missing tiles
135
136 auto result = generator_->ParseReplaceTileCommand(command, nullptr);
137
138 EXPECT_FALSE(result.ok());
139 EXPECT_THAT(result.status().message(),
140 ::testing::HasSubstr("Invalid replace-tile command format"));
141}
142
143// ============================================================================
144// GenerateFromCommands Tests
145// ============================================================================
146
147TEST_F(Tile16ProposalGeneratorTest, GenerateFromCommands_MultipleCommands) {
148 std::vector<std::string> commands = {
149 "overworld set-tile --map 0 --x 10 --y 20 --tile 0x02E",
150 "overworld set-area --map 0 --x 5 --y 5 --width 2 --height 2 --tile 0x030"
151 };
152
153 auto result = generator_->GenerateFromCommands(
154 "Test prompt", commands, "test_ai", nullptr);
155
156 ASSERT_TRUE(result.ok()) << result.status().message();
157 EXPECT_EQ(result->changes.size(), 5); // 1 from set-tile + 4 from set-area
158 EXPECT_EQ(result->prompt, "Test prompt");
159 EXPECT_EQ(result->ai_service, "test_ai");
160 EXPECT_EQ(result->status, Tile16Proposal::Status::PENDING);
161}
162
163TEST_F(Tile16ProposalGeneratorTest, GenerateFromCommands_EmptyCommands) {
164 std::vector<std::string> commands = {};
165
166 auto result = generator_->GenerateFromCommands(
167 "Test prompt", commands, "test_ai", nullptr);
168
169 EXPECT_FALSE(result.ok());
170 EXPECT_THAT(result.status().message(),
171 ::testing::HasSubstr("No valid tile16 changes found"));
172}
173
174TEST_F(Tile16ProposalGeneratorTest, GenerateFromCommands_IgnoresComments) {
175 std::vector<std::string> commands = {
176 "# This is a comment",
177 "overworld set-tile --map 0 --x 10 --y 20 --tile 0x02E",
178 "# Another comment",
179 "" // Empty line
180 };
181
182 auto result = generator_->GenerateFromCommands(
183 "Test prompt", commands, "test_ai", nullptr);
184
185 ASSERT_TRUE(result.ok());
186 EXPECT_EQ(result->changes.size(), 1); // Only the valid command
187}
188
189// ============================================================================
190// Tile16Change Tests
191// ============================================================================
192
193TEST_F(Tile16ProposalGeneratorTest, Tile16Change_ToString) {
194 Tile16Change change;
195 change.map_id = 5;
196 change.x = 10;
197 change.y = 20;
198 change.old_tile = 0x02E;
199 change.new_tile = 0x030;
200
201 std::string result = change.ToString();
202
203 EXPECT_THAT(result, ::testing::HasSubstr("Map 5"));
204 EXPECT_THAT(result, ::testing::HasSubstr("(10,20)"));
205 EXPECT_THAT(result, ::testing::HasSubstr("0x2e"));
206 EXPECT_THAT(result, ::testing::HasSubstr("0x30"));
207}
208
209// ============================================================================
210// Proposal Serialization Tests
211// ============================================================================
212
213TEST_F(Tile16ProposalGeneratorTest, Proposal_ToJsonAndFromJson) {
214 Tile16Proposal original;
215 original.id = "test_id_123";
216 original.prompt = "Test prompt";
217 original.ai_service = "gemini";
218 original.reasoning = "Test reasoning";
220
221 Tile16Change change;
222 change.map_id = 5;
223 change.x = 10;
224 change.y = 20;
225 change.old_tile = 0x02E;
226 change.new_tile = 0x030;
227 original.changes.push_back(change);
228
229 std::string json = original.ToJson();
230 auto result = Tile16Proposal::FromJson(json);
231
232 ASSERT_TRUE(result.ok()) << result.status().message();
233 EXPECT_EQ(result->id, original.id);
234 EXPECT_EQ(result->prompt, original.prompt);
235 EXPECT_EQ(result->ai_service, original.ai_service);
236 EXPECT_EQ(result->reasoning, original.reasoning);
237 EXPECT_EQ(result->status, original.status);
238 EXPECT_EQ(result->changes.size(), 1);
239 EXPECT_EQ(result->changes[0].map_id, 5);
240}
241
242} // namespace
243} // namespace cli
244} // namespace yaze
Main namespace for the application.
Represents a single tile16 change in a proposal.
Represents a proposal for tile16 edits on the overworld.
std::vector< Tile16Change > changes
static absl::StatusOr< Tile16Proposal > FromJson(const std::string &json)