85 log_msg(ERROR,
"Character",
"Database connection is not open");
90 int rc = sqlite3_prepare_v2(db_connection->db, SQL_INSERT_CHARACTER, -1, &stmt, NULL);
91 if (rc != SQLITE_OK) {
92 log_msg(ERROR,
"Character",
"Failed to prepare statement: %s", sqlite3_errmsg(db_connection->db));
96 rc = sqlite3_bind_int(stmt, 1, character.max_resources.health);
97 if (rc != SQLITE_OK) {
98 log_msg(ERROR,
"Character",
"Failed to bind max health: %s", sqlite3_errmsg(db_connection->db));
99 sqlite3_finalize(stmt);
102 rc = sqlite3_bind_int(stmt, 2, character.max_resources.mana);
103 if (rc != SQLITE_OK) {
104 log_msg(ERROR,
"Character",
"Failed to bind max mana: %s", sqlite3_errmsg(db_connection->db));
105 sqlite3_finalize(stmt);
108 rc = sqlite3_bind_int(stmt, 3, character.max_resources.stamina);
109 if (rc != SQLITE_OK) {
110 log_msg(ERROR,
"Character",
"Failed to bind max stamina: %s", sqlite3_errmsg(db_connection->db));
111 sqlite3_finalize(stmt);
114 rc = sqlite3_bind_int(stmt, 4, character.current_resources.health);
115 if (rc != SQLITE_OK) {
116 log_msg(ERROR,
"Character",
"Failed to bind current health: %s", sqlite3_errmsg(db_connection->db));
117 sqlite3_finalize(stmt);
120 rc = sqlite3_bind_int(stmt, 5, character.current_resources.mana);
121 if (rc != SQLITE_OK) {
122 log_msg(ERROR,
"Character",
"Failed to bind current mana: %s", sqlite3_errmsg(db_connection->db));
123 sqlite3_finalize(stmt);
126 rc = sqlite3_bind_int(stmt, 6, character.current_resources.stamina);
127 if (rc != SQLITE_OK) {
128 log_msg(ERROR,
"Character",
"Failed to bind current stamina: %s", sqlite3_errmsg(db_connection->db));
129 sqlite3_finalize(stmt);
132 rc = sqlite3_bind_int(stmt, 7, character.defenses.armor);
133 if (rc != SQLITE_OK) {
134 log_msg(ERROR,
"Character",
"Failed to bind armor: %s", sqlite3_errmsg(db_connection->db));
135 sqlite3_finalize(stmt);
138 rc = sqlite3_bind_int(stmt, 8, character.defenses.magic_resist);
139 if (rc != SQLITE_OK) {
140 log_msg(ERROR,
"Character",
"Failed to bind magic resist: %s", sqlite3_errmsg(db_connection->db));
141 sqlite3_finalize(stmt);
144 rc = sqlite3_bind_int(stmt, 9, character.level);
145 if (rc != SQLITE_OK) {
146 log_msg(ERROR,
"Character",
"Failed to bind level: %s", sqlite3_errmsg(db_connection->db));
147 sqlite3_finalize(stmt);
150 rc = sqlite3_bind_int(stmt, 10, character.xp);
151 if (rc != SQLITE_OK) {
152 log_msg(ERROR,
"Character",
"Failed to bind xp: %s", sqlite3_errmsg(db_connection->db));
153 sqlite3_finalize(stmt);
156 rc = sqlite3_bind_int(stmt, 11, character.xp_reward);
157 if (rc != SQLITE_OK) {
158 log_msg(ERROR,
"Character",
"Failed to bind xp reward: %s", sqlite3_errmsg(db_connection->db));
159 sqlite3_finalize(stmt);
162 rc = sqlite3_bind_int(stmt, 12, character.skill_points);
163 if (rc != SQLITE_OK) {
164 log_msg(ERROR,
"Character",
"Failed to bind skill points: %s", sqlite3_errmsg(db_connection->db));
165 sqlite3_finalize(stmt);
168 rc = sqlite3_bind_int(stmt, 13, character.base_stats.strength);
169 if (rc != SQLITE_OK) {
170 log_msg(ERROR,
"Character",
"Failed to bind base strength: %s", sqlite3_errmsg(db_connection->db));
171 sqlite3_finalize(stmt);
174 rc = sqlite3_bind_int(stmt, 14, character.base_stats.intelligence);
175 if (rc != SQLITE_OK) {
176 log_msg(ERROR,
"Character",
"Failed to bind base intelligence: %s", sqlite3_errmsg(db_connection->db));
177 sqlite3_finalize(stmt);
180 rc = sqlite3_bind_int(stmt, 15, character.base_stats.dexterity);
181 if (rc != SQLITE_OK) {
182 log_msg(ERROR,
"Character",
"Failed to bind base dexterity: %s", sqlite3_errmsg(db_connection->db));
183 sqlite3_finalize(stmt);
186 rc = sqlite3_bind_int(stmt, 16, character.base_stats.constitution);
187 if (rc != SQLITE_OK) {
188 log_msg(ERROR,
"Character",
"Failed to bind base constitution: %s", sqlite3_errmsg(db_connection->db));
189 sqlite3_finalize(stmt);
192 rc = sqlite3_bind_int(stmt, 17, character.current_stats.strength);
193 if (rc != SQLITE_OK) {
194 log_msg(ERROR,
"Character",
"Failed to bind current strength: %s", sqlite3_errmsg(db_connection->db));
195 sqlite3_finalize(stmt);
198 rc = sqlite3_bind_int(stmt, 18, character.current_stats.intelligence);
199 if (rc != SQLITE_OK) {
200 log_msg(ERROR,
"Character",
"Failed to bind current intelligence: %s", sqlite3_errmsg(db_connection->db));
201 sqlite3_finalize(stmt);
204 rc = sqlite3_bind_int(stmt, 19, character.current_stats.dexterity);
205 if (rc != SQLITE_OK) {
206 log_msg(ERROR,
"Character",
"Failed to bind current dexterity: %s", sqlite3_errmsg(db_connection->db));
207 sqlite3_finalize(stmt);
210 rc = sqlite3_bind_int(stmt, 20, character.current_stats.constitution);
211 if (rc != SQLITE_OK) {
212 log_msg(ERROR,
"Character",
"Failed to bind current constitution: %s", sqlite3_errmsg(db_connection->db));
213 sqlite3_finalize(stmt);
217 rc = sqlite3_step(stmt);
219 const sqlite3_int64 character_id = sqlite3_last_insert_rowid(db_connection->db);
220 if (rc != SQLITE_DONE) {
221 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
222 sqlite3_finalize(stmt);
226 sqlite3_finalize(stmt);
229 sqlite3_stmt* stmt_player;
230 rc = sqlite3_prepare_v2(db_connection->db, SQL_INSERT_PLAYER, -1, &stmt_player, NULL);
231 if (rc != SQLITE_OK) {
232 log_msg(ERROR,
"Character",
"Failed to prepare statement: %s", sqlite3_errmsg(db_connection->db));
236 rc = sqlite3_bind_int64(stmt_player, 1, character_id);
237 if (rc != SQLITE_OK) {
238 log_msg(ERROR,
"Character",
"Failed to bind character ID: %s", sqlite3_errmsg(db_connection->db));
239 sqlite3_finalize(stmt_player);
242 rc = sqlite3_bind_int64(stmt_player, 2, game_state_id);
243 if (rc != SQLITE_OK) {
244 log_msg(ERROR,
"Character",
"Failed to bind game state ID: %s", sqlite3_errmsg(db_connection->db));
245 sqlite3_finalize(stmt_player);
248 rc = sqlite3_bind_text(stmt_player, 3, character.name, -1, SQLITE_STATIC);
249 if (rc != SQLITE_OK) {
250 log_msg(ERROR,
"Character",
"Failed to bind character name: %s", sqlite3_errmsg(db_connection->db));
251 sqlite3_finalize(stmt_player);
255 rc = sqlite3_step(stmt_player);
256 if (rc != SQLITE_DONE) {
257 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
258 sqlite3_finalize(stmt_player);
265 sqlite3_finalize(stmt_player);
271 int rc = sqlite3_prepare_v2(db_connection->db, SQL_INSERT_INVENTORY, -1, &stmt, NULL);
272 if (rc != SQLITE_OK) {
273 log_msg(ERROR,
"Character",
"Failed to prepare statement: %s", sqlite3_errmsg(db_connection->db));
277 rc = sqlite3_bind_int(stmt, 1, 0);
278 if (rc != SQLITE_OK) {
279 log_msg(ERROR,
"Character",
"Failed to bind inventory type: %s", sqlite3_errmsg(db_connection->db));
280 sqlite3_finalize(stmt);
284 rc = sqlite3_step(stmt);
287 const sqlite3_int64 inventory_gear_id = sqlite3_last_insert_rowid(db_connection->db);
288 if (rc != SQLITE_DONE) {
289 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
290 sqlite3_finalize(stmt);
294 sqlite3_finalize(stmt);
297 sqlite3_stmt* stmt_potion;
298 rc = sqlite3_prepare_v2(db_connection->db, SQL_INSERT_INVENTORY, -1, &stmt_potion, NULL);
299 if (rc != SQLITE_OK) {
300 log_msg(ERROR,
"Character",
"Failed to prepare statement: %s", sqlite3_errmsg(db_connection->db));
304 rc = sqlite3_bind_int(stmt_potion, 1, 1);
305 if (rc != SQLITE_OK) {
306 log_msg(ERROR,
"Character",
"Failed to bind inventory type: %s", sqlite3_errmsg(db_connection->db));
307 sqlite3_finalize(stmt_potion);
311 rc = sqlite3_step(stmt_potion);
313 const sqlite3_int64 inventory_potion_id = sqlite3_last_insert_rowid(db_connection->db);
314 if (rc != SQLITE_DONE) {
315 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
316 sqlite3_finalize(stmt_potion);
320 sqlite3_finalize(stmt_potion);
323 for (
int i = 0; i < character.gear_count; i++) {
325 sqlite3_stmt* stmt_gear_save;
326 rc = sqlite3_prepare_v2(db_connection->db, SQL_INSERT_INVENTORY_GEAR, -1, &stmt_gear_save, NULL);
327 if (rc != SQLITE_OK) {
328 log_msg(ERROR,
"Character",
"Failed to prepare statement: %s", sqlite3_errmsg(db_connection->db));
332 rc = sqlite3_bind_int64(stmt_gear_save, 1, inventory_gear_id);
333 if (rc != SQLITE_OK) {
334 log_msg(ERROR,
"Character",
"Failed to bind inventory ID: %s", sqlite3_errmsg(db_connection->db));
335 sqlite3_finalize(stmt_gear_save);
339 rc = sqlite3_bind_int(stmt_gear_save, 2, character.gear_inventory[i]->gear_identifier);
340 if (rc != SQLITE_OK) {
341 log_msg(ERROR,
"Character",
"Failed to bind gear type: %s", sqlite3_errmsg(db_connection->db));
342 sqlite3_finalize(stmt_gear_save);
346 rc = sqlite3_bind_int(stmt_gear_save, 3, 0);
348 if (rc != SQLITE_OK) {
349 log_msg(ERROR,
"Character",
"Failed to bind equipped status: %s", sqlite3_errmsg(db_connection->db));
350 sqlite3_finalize(stmt_gear_save);
354 rc = sqlite3_step(stmt_gear_save);
355 if (rc != SQLITE_DONE) {
356 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
357 sqlite3_finalize(stmt_gear_save);
361 sqlite3_finalize(stmt_gear_save);
365 for (
int i = 0; i < MAX_SLOT; i++) {
366 if (character.equipment[i] != NULL) {
368 sqlite3_stmt* stmt_gear_save;
369 rc = sqlite3_prepare_v2(db_connection->db, SQL_INSERT_INVENTORY_GEAR, -1, &stmt_gear_save, NULL);
370 if (rc != SQLITE_OK) {
371 log_msg(ERROR,
"Character",
"Failed to prepare statement: %s", sqlite3_errmsg(db_connection->db));
375 rc = sqlite3_bind_int64(stmt_gear_save, 1, inventory_gear_id);
376 if (rc != SQLITE_OK) {
377 log_msg(ERROR,
"Character",
"Failed to bind inventory ID: %s", sqlite3_errmsg(db_connection->db));
378 sqlite3_finalize(stmt_gear_save);
382 rc = sqlite3_bind_int(stmt_gear_save, 2, character.equipment[i]->gear_identifier);
383 if (rc != SQLITE_OK) {
384 log_msg(ERROR,
"Character",
"Failed to bind gear type: %s", sqlite3_errmsg(db_connection->db));
385 sqlite3_finalize(stmt_gear_save);
389 rc = sqlite3_bind_int(stmt_gear_save, 3, 1);
391 if (rc != SQLITE_OK) {
392 log_msg(ERROR,
"Character",
"Failed to bind equipped status: %s", sqlite3_errmsg(db_connection->db));
393 sqlite3_finalize(stmt_gear_save);
397 rc = sqlite3_step(stmt_gear_save);
398 if (rc != SQLITE_DONE) {
399 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
400 sqlite3_finalize(stmt_gear_save);
404 sqlite3_finalize(stmt_gear_save);
409 for (
int i = 0; i < character.potion_count; i++) {
411 sqlite3_stmt* stmt_potion_save;
412 rc = sqlite3_prepare_v2(db_connection->db, SQL_INSERT_INVENTORY_POTION, -1, &stmt_potion_save, NULL);
413 if (rc != SQLITE_OK) {
414 log_msg(ERROR,
"Character",
"Failed to prepare statement: %s", sqlite3_errmsg(db_connection->db));
418 rc = sqlite3_bind_int64(stmt_potion_save, 1, inventory_potion_id);
419 if (rc != SQLITE_OK) {
420 log_msg(ERROR,
"Character",
"Failed to bind inventory ID: %s", sqlite3_errmsg(db_connection->db));
421 sqlite3_finalize(stmt_potion_save);
425 rc = sqlite3_bind_int(stmt_potion_save, 2, character.potion_inventory[i]->effectType);
426 if (rc != SQLITE_OK) {
427 log_msg(ERROR,
"Character",
"Failed to bind potion type: %s", sqlite3_errmsg(db_connection->db));
428 sqlite3_finalize(stmt_potion_save);
432 rc = sqlite3_step(stmt_potion_save);
433 if (rc != SQLITE_DONE) {
434 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
435 sqlite3_finalize(stmt_potion_save);
439 sqlite3_finalize(stmt_potion_save);
443 sqlite3_stmt* stmt_character_inventory;
444 rc = sqlite3_prepare_v2(db_connection->db, SQL_INSERT_CHARACTER_INVENTORY, -1, &stmt_character_inventory, NULL);
445 if (rc != SQLITE_OK) {
446 log_msg(ERROR,
"Character",
"Failed to prepare statement: %s", sqlite3_errmsg(db_connection->db));
450 rc = sqlite3_bind_int64(stmt_character_inventory, 1, character_id);
451 if (rc != SQLITE_OK) {
452 log_msg(ERROR,
"Character",
"Failed to bind character ID: %s", sqlite3_errmsg(db_connection->db));
453 sqlite3_finalize(stmt_character_inventory);
457 rc = sqlite3_bind_int64(stmt_character_inventory, 2, inventory_gear_id);
458 if (rc != SQLITE_OK) {
459 log_msg(ERROR,
"Character",
"Failed to bind inventory ID: %s", sqlite3_errmsg(db_connection->db));
460 sqlite3_finalize(stmt_character_inventory);
464 rc = sqlite3_step(stmt_character_inventory);
465 if (rc != SQLITE_DONE) {
466 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
467 sqlite3_finalize(stmt_character_inventory);
471 sqlite3_finalize(stmt_character_inventory);
474 sqlite3_stmt* stmt_character_inventory_potion;
475 rc = sqlite3_prepare_v2(db_connection->db, SQL_INSERT_CHARACTER_INVENTORY, -1, &stmt_character_inventory_potion, NULL);
476 if (rc != SQLITE_OK) {
477 log_msg(ERROR,
"Character",
"Failed to prepare statement: %s", sqlite3_errmsg(db_connection->db));
481 rc = sqlite3_bind_int64(stmt_character_inventory_potion, 1, character_id);
482 if (rc != SQLITE_OK) {
483 log_msg(ERROR,
"Character",
"Failed to bind character ID: %s", sqlite3_errmsg(db_connection->db));
484 sqlite3_finalize(stmt_character_inventory_potion);
488 rc = sqlite3_bind_int64(stmt_character_inventory_potion, 2, inventory_potion_id);
489 if (rc != SQLITE_OK) {
490 log_msg(ERROR,
"Character",
"Failed to bind inventory ID: %s", sqlite3_errmsg(db_connection->db));
491 sqlite3_finalize(stmt_character_inventory_potion);
495 rc = sqlite3_step(stmt_character_inventory_potion);
496 if (rc != SQLITE_DONE) {
497 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
498 sqlite3_finalize(stmt_character_inventory_potion);
502 sqlite3_finalize(stmt_character_inventory_potion);
509 log_msg(ERROR,
"Character",
"Database connection is not open");
514 sqlite3_int64 character_id = 0;
515 int rc = sqlite3_prepare_v2(db_connection->db, SQL_SELECT_CHARACTER, -1, &stmt, NULL);
516 if (rc != SQLITE_OK) {
517 log_msg(ERROR,
"Character",
"Failed to prepare statement: %s", sqlite3_errmsg(db_connection->db));
521 rc = sqlite3_bind_int(stmt, 1, game_state_id);
522 if (rc != SQLITE_OK) {
523 log_msg(ERROR,
"Character",
"Failed to bind game state ID: %s", sqlite3_errmsg(db_connection->db));
524 sqlite3_finalize(stmt);
528 rc = sqlite3_step(stmt);
529 if (rc == SQLITE_ROW) {
531 const char* name = (
const char*) sqlite3_column_text(stmt, 0);
532 character->max_resources.health = sqlite3_column_int(stmt, 1);
533 character->max_resources.mana = sqlite3_column_int(stmt, 2);
534 character->max_resources.stamina = sqlite3_column_int(stmt, 3);
535 character->current_resources.health = sqlite3_column_int(stmt, 4);
536 character->current_resources.mana = sqlite3_column_int(stmt, 5);
537 character->current_resources.stamina = sqlite3_column_int(stmt, 6);
538 character->defenses.armor = sqlite3_column_int(stmt, 7);
539 character->defenses.magic_resist = sqlite3_column_int(stmt, 8);
540 character->level = sqlite3_column_int(stmt, 9);
541 character->xp = sqlite3_column_int(stmt, 10);
542 character->xp_reward = sqlite3_column_int(stmt, 11);
543 character->skill_points = sqlite3_column_int(stmt, 12);
544 character->base_stats.strength = sqlite3_column_int(stmt, 13);
545 character->base_stats.intelligence = sqlite3_column_int(stmt, 14);
546 character->base_stats.dexterity = sqlite3_column_int(stmt, 15);
547 character->base_stats.constitution = sqlite3_column_int(stmt, 16);
548 character->current_stats.strength = sqlite3_column_int(stmt, 17);
549 character->current_stats.intelligence = sqlite3_column_int(stmt, 18);
550 character->current_stats.dexterity = sqlite3_column_int(stmt, 19);
551 character->current_stats.constitution = sqlite3_column_int(stmt, 20);
552 character_id = sqlite3_column_int64(stmt, 21);
555 snprintf(character->name,
sizeof(character->name),
"%s", name);
558 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
561 sqlite3_finalize(stmt);
563 sqlite3_stmt* stmt_gear;
564 rc = sqlite3_prepare_v2(db_connection->db, SQL_SELECT_GEAR, -1, &stmt_gear, NULL);
565 if (rc != SQLITE_OK) {
566 log_msg(ERROR,
"Character",
"Failed to prepare statement: %s", sqlite3_errmsg(db_connection->db));
570 rc = sqlite3_bind_int64(stmt_gear, 1, character_id);
571 if (rc != SQLITE_OK) {
572 log_msg(ERROR,
"Character",
"Failed to bind character ID: %s", sqlite3_errmsg(db_connection->db));
573 sqlite3_finalize(stmt_gear);
577 rc = sqlite3_bind_int(stmt_gear, 2, 1);
578 if (rc != SQLITE_OK) {
579 log_msg(ERROR,
"Character",
"Failed to bind equipped status: %s", sqlite3_errmsg(db_connection->db));
580 sqlite3_finalize(stmt_gear);
584 rc = sqlite3_step(stmt_gear);
586 while (rc == SQLITE_ROW) {
587 gear_t* loaded_gear = gear_table->gears[sqlite3_column_int(stmt_gear, 0)];
589 rc = sqlite3_step(stmt_gear);
590 if (rc != SQLITE_DONE && rc != SQLITE_ROW) {
591 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
592 sqlite3_finalize(stmt_gear);
598 rc = sqlite3_reset(stmt_gear);
599 if (rc != SQLITE_OK) {
600 log_msg(ERROR,
"Character",
"Failed to reset statement: %s", sqlite3_errmsg(db_connection->db));
601 sqlite3_finalize(stmt_gear);
606 rc = sqlite3_bind_int(stmt_gear, 2, 0);
607 if (rc != SQLITE_OK) {
608 log_msg(ERROR,
"Character",
"Failed to bind unequipped status: %s", sqlite3_errmsg(db_connection->db));
609 sqlite3_finalize(stmt_gear);
613 rc = sqlite3_step(stmt_gear);
615 while (rc == SQLITE_ROW) {
616 gear_t* loaded_gear = gear_table->gears[sqlite3_column_int(stmt_gear, 0)];
617 character->gear_inventory[character->gear_count++] = loaded_gear;
618 rc = sqlite3_step(stmt_gear);
619 if (rc != SQLITE_DONE && rc != SQLITE_ROW) {
620 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
621 sqlite3_finalize(stmt_gear);
626 sqlite3_finalize(stmt_gear);
629 sqlite3_stmt* stmt_potion;
630 rc = sqlite3_prepare_v2(db_connection->db, SQL_SELECT_POTION, -1, &stmt_potion, NULL);
631 if (rc != SQLITE_OK) {
632 log_msg(ERROR,
"Character",
"Failed to prepare statement: %s", sqlite3_errmsg(db_connection->db));
636 rc = sqlite3_bind_int64(stmt_potion, 1, character_id);
637 if (rc != SQLITE_OK) {
638 log_msg(ERROR,
"Character",
"Failed to bind character ID: %s", sqlite3_errmsg(db_connection->db));
639 sqlite3_finalize(stmt_potion);
643 rc = sqlite3_step(stmt_potion);
645 while (rc == SQLITE_ROW) {
646 potion_t* loaded_potion = &potion_table->potions[sqlite3_column_int(stmt_potion, 0)];
647 character->potion_inventory[character->potion_count++] = loaded_potion;
648 rc = sqlite3_step(stmt_potion);
649 if (rc != SQLITE_DONE && rc != SQLITE_ROW) {
650 log_msg(ERROR,
"Character",
"Failed to execute statement: %s", sqlite3_errmsg(db_connection->db));
651 sqlite3_finalize(stmt_potion);
656 sqlite3_finalize(stmt_potion);