LCOV - code coverage report
Current view: top level - src - Core.c (source / functions) Hit Total Coverage
Test: lcov-output.info Lines: 366 386 94.8 %
Date: 2024-09-02 18:48:12 Functions: 44 45 97.8 %

          Line data    Source code
       1             : /*
       2             : Created by Daniel Monteiro on 2019-07-26.
       3             : */
       4             : #include <stddef.h>
       5             : 
       6             : #ifdef __MWERKS__
       7             : #define CLI_BUILD
       8             : #endif
       9             : 
      10             : #ifndef SMD
      11             : 
      12             : #include <assert.h>
      13             : #include <stdlib.h>
      14             : #include <stdio.h>
      15             : #include <string.h>
      16             : 
      17             : #ifdef WIN32
      18             : #include "Win32Int.h"
      19             : #else
      20             : 
      21             : #include <stdint.h>
      22             : 
      23             : #endif
      24             : #else
      25             : #include <genesis.h>
      26             : #endif
      27             : 
      28             : #include "Enums.h"
      29             : #include "Common.h"
      30             : #include "Core.h"
      31             : 
      32             : #define WALK_STEP 1
      33             : 
      34             : /**
      35             :  * there's an implicit dummy first
      36             :  */
      37             : int roomCount = 1;
      38             : /**
      39             :  *
      40             :  */
      41             : struct Room rooms[TOTAL_ROOMS];
      42             : /**
      43             :  *
      44             :  */
      45             : uint8_t itemsCount = 0;
      46             : /**
      47             :  *
      48             :  */
      49             : struct Item item[TOTAL_ITEMS];
      50             : /*
      51             :  *
      52             :  */
      53             : struct ObjectNode objectNodes[TOTAL_ITEMS];
      54             : /**
      55             :  *
      56             :  */
      57             : struct ObjectNode collectedObjectHead;
      58             : /**
      59             :  *
      60             :  */
      61             : struct ObjectNode roomObjectHeads[TOTAL_ROOMS];
      62             : /**
      63             :  *
      64             :  */
      65             : struct ObjectNode *collectedObject = NULL;
      66             : /**
      67             :  *
      68             :  */
      69             : uint8_t playerLocation = 1;
      70             : /**
      71             :  *
      72             :  */
      73             : enum EDirection playerDirection;
      74             : /**
      75             :  *
      76             :  */
      77             : uint8_t playerRank;
      78             : /**
      79             :  *
      80             :  */
      81             : enum EGameStates gameStatus;
      82             : /**
      83             :  *
      84             :  */
      85             : struct WorldPosition playerPosition;
      86             : /**
      87             :  *
      88             :  */
      89             : ErrorHandlerCallback errorHandlerCallback = NULL;
      90             : 
      91           8 : void writeToLog(const char *errorMsg) {
      92             : #ifdef HAS_STDIO
      93             :     if (errorHandlerCallback == NULL) {
      94             :         puts("-------");
      95             :         puts(errorMsg);
      96             :         puts("--!!---");
      97             :     } else {
      98             :         errorHandlerCallback(errorMsg);
      99             :     }
     100             : #else
     101             :     /* We assume the error handler was already set. If you don't have stdio, you probably know what you're doing */
     102           8 :     errorHandlerCallback(errorMsg);
     103             : #endif
     104           8 : }
     105             : 
     106           2 : void cantBeUsedCallback(struct Item *item) {
     107             :     (void)item;
     108           2 :     defaultLogger("You can't use it like this.");
     109           2 : }
     110             : 
     111           1 : void cantBeUsedWithOthersCallback(struct Item *item1, struct Item *item2) {
     112             :     (void)item1;
     113             :     (void)item2;
     114           1 :     defaultLogger("Nothing happens.");
     115           1 : }
     116             : 
     117        1866 : struct Item *addItem(const char *description,
     118             : #ifdef INCLUDE_ITEM_DESCRIPTIONS
     119             :         const char *info,
     120             : #endif
     121             : #ifdef ITEMS_HAVE_WEIGHT
     122             :         uint8_t weight,
     123             : #endif
     124             :                      uint8_t pickable,
     125             :                      int8_t positionX,
     126             :                      int8_t positionY) {
     127             : 
     128        1866 :     struct Item *toReturn = &item[itemsCount];
     129             : 
     130        1866 :     toReturn->index = itemsCount++;
     131        1866 :     toReturn->name = description;
     132             : #ifdef INCLUDE_ITEM_DESCRIPTIONS
     133             :     toReturn->info = info;
     134             : #endif
     135        1866 :     toReturn->pickable = pickable;
     136        1866 :     toReturn->position.x = positionX;
     137        1866 :     toReturn->position.y = positionY;
     138             : 
     139        1866 :     toReturn->useCallback = cantBeUsedCallback;
     140        1866 :     toReturn->useWithCallback = cantBeUsedWithOthersCallback;
     141             : 
     142        1866 :     return toReturn;
     143             : }
     144             : 
     145        1219 : struct Room *addRoom(
     146             :         const char *name,
     147             : #ifdef INCLUDE_ROOM_DESCRIPTIONS
     148             :         const char *info,
     149             : #endif
     150             :         uint8_t sizeX, uint8_t sizeY, uint8_t chanceOfRandomBattle, const int8_t connections[6]) {
     151             : 
     152        1219 :     struct Room *toReturn = &rooms[roomCount];
     153        1219 :     toReturn->name = name;
     154             : #ifdef INCLUDE_ROOM_DESCRIPTIONS
     155             :     toReturn->info = info;
     156             : #endif
     157        1219 :     toReturn->sizeX = sizeX;
     158        1219 :     toReturn->sizeY = sizeY;
     159        1219 :     toReturn->chanceOfRandomBattle = chanceOfRandomBattle;
     160             : 
     161        1219 :     memCopyToFrom((void*)toReturn->connections, (void*)connections, 6);
     162             : 
     163             :     /* add list head to make manipulations easier */
     164        1219 :     toReturn->itemsPresent = &roomObjectHeads[roomCount++];
     165        1219 :     memFill(toReturn->itemsPresent, 0, sizeof(struct ObjectNode));
     166             : 
     167        1219 :     return toReturn;
     168             : }
     169             : 
     170             : LogDelegate defaultLogger = writeToLog;
     171             : 
     172          59 : void setErrorHandlerCallback(ErrorHandlerCallback callback) {
     173          59 :     errorHandlerCallback = callback;
     174          59 : }
     175             : 
     176         146 : struct WorldPosition *getPlayerPosition(void) {
     177         146 :     return &playerPosition;
     178             : }
     179             : 
     180           4 : void setPlayerPosition(struct WorldPosition *pos) {
     181           4 :     playerPosition.x = pos->x;
     182           4 :     playerPosition.y = pos->y;
     183           4 : }
     184             : 
     185             : #ifndef CAN_PICK_OBJECT_AT_ANY_DISTANCE
     186         129 : uint8_t isCloseToObject(struct WorldPosition *pos, struct Item *_item) {
     187         129 :     return (abs(pos->x - _item->position.x) + abs(pos->y - _item->position.y)) <= 1;
     188             : }
     189             : #endif
     190             : 
     191          14 : enum EGameStates getGameStatus(void) {
     192          14 :     return gameStatus;
     193             : }
     194             : 
     195          24 : struct ObjectNode *getPlayerItems(void) {
     196          24 :     return collectedObject->next;
     197             : }
     198             : 
     199         104 : struct Item *getItemNamed(const char *name) {
     200             :     uint8_t c;
     201             : 
     202        1221 :     for (c = 0; c < itemsCount; ++c) {
     203        1220 :         if (!strcmp(item[c].name, name)) {
     204         103 :             return &item[c];
     205             :         }
     206             :     }
     207             : 
     208           1 :     return NULL;
     209             : }
     210             : 
     211             : #ifdef MORE_OBJECTS
     212          17 : uint8_t getRoomIdByName(const char *name) {
     213             :     uint8_t c;
     214             : 
     215          17 :     if (name != NULL) {
     216         215 :         for (c = 1; c < roomCount; ++c) {
     217         214 :             if (!strcmp(rooms[c].name, name)) {
     218          15 :                 return c;
     219             :             }
     220             :         }
     221             :     }
     222             : 
     223           2 :     return 0;
     224             : }
     225             : #endif
     226             : 
     227          87 : struct Room *getRoomByName(const char *name) {
     228             :     uint8_t c;
     229             : 
     230          87 :     if (name != NULL) {
     231         724 :         for (c = 1; c < roomCount; ++c) {
     232         723 :             if (!strcmp(rooms[c].name, name)) {
     233          86 :                 return &rooms[c];
     234             :             }
     235             :         }
     236             :     }
     237             : 
     238           1 :     return NULL;
     239             : }
     240             : 
     241        1714 : void addObjectToList(struct Item *itemToAdd, struct ObjectNode *listHead) {
     242        1714 :     struct ObjectNode *head = listHead;
     243             : 
     244        2697 :     while (head->next != NULL) {
     245         984 :         if (getItem(head->item) == itemToAdd) {
     246             :             /* Object already belongs to the list! */
     247           1 :             return;
     248             :         }
     249             : 
     250         983 :         head = head->next;
     251             :     }
     252             : 
     253        1713 :     head->next = &objectNodes[itemToAdd->index];
     254        1713 :     memFill(head->next, 0, sizeof(struct ObjectNode));
     255        1713 :     head->next->item = itemToAdd->index;
     256             : }
     257             : 
     258          49 : void removeObjectFromList(struct Item *itemToRemove, struct ObjectNode *listHead) {
     259          49 :     struct ObjectNode *head = listHead->next;
     260          49 :     struct ObjectNode *prev = listHead;
     261             : 
     262         134 :     while (head != NULL) {
     263         134 :         if (head->item == itemToRemove->index) {
     264          49 :             prev->next = head->next;
     265          49 :             return;
     266             :         }
     267             : 
     268          85 :         prev = head;
     269          85 :         head = head->next;
     270             :     }
     271             :     /* Object doesn't belong to the list! */
     272             : }
     273             : 
     274        1712 : void removeObjectFromRoom(struct Item *itemToRemove) {
     275        1712 :     if (itemToRemove->roomId != 0) {
     276          38 :         removeObjectFromList(itemToRemove, rooms[itemToRemove->roomId].itemsPresent);
     277          38 :         itemToRemove->roomId = 0;
     278             :     }
     279        1712 : }
     280             : 
     281             : 
     282        1583 : void addObjectToRoom(uint8_t roomId, struct Item *itemToAdd) {
     283        1583 :     struct Room *roomToAddObject = &rooms[roomId];
     284        1583 :     removeObjectFromRoom(itemToAdd);
     285        1583 :     addObjectToList(itemToAdd, roomToAddObject->itemsPresent);
     286        1583 :     itemToAdd->roomId = roomId;
     287        1583 : }
     288             : 
     289          11 : void dropObjectToRoom(uint8_t roomId, struct Item *itemToDrop) {
     290             : #ifdef CLI_BUILD
     291          11 :     if (itemToDrop->roomId != 0) {
     292           0 :         defaultLogger("Object not present to drop");
     293             :     }
     294             : #endif
     295             : 
     296          11 :     if (!itemToDrop->pickable) {
     297           0 :         defaultLogger("Can't drop this");
     298           0 :         return;
     299             :     }
     300             : 
     301          11 :     removeObjectFromList(itemToDrop, collectedObject);
     302          11 :     addObjectToRoom(roomId, itemToDrop);
     303             : 
     304          11 :     if (itemToDrop->dropCallback != NULL) {
     305           7 :         itemToDrop->dropCallback(itemToDrop);
     306             :     }
     307             : }
     308             : 
     309         129 : void pickObject(struct Item *itemToPick) {
     310             : #ifndef CAN_PICK_OBJECT_AT_ANY_DISTANCE
     311         129 :     if (!isCloseToObject(getPlayerPosition(), itemToPick)) {
     312           0 :         return;
     313             :     }
     314             : #endif
     315             : 
     316         129 :     if (!itemToPick->pickable) {
     317           1 :         defaultLogger("Can't pick it up");
     318           1 :         return;
     319             :     }
     320             : 
     321         128 :     removeObjectFromRoom(itemToPick);
     322         128 :     addObjectToList(itemToPick, collectedObject);
     323             : 
     324         128 :     if (itemToPick->pickCallback != NULL) {
     325          14 :         itemToPick->pickCallback(itemToPick);
     326             :     }
     327             : }
     328             : 
     329          10 : uint8_t getPlayerRank(void) {
     330          10 :     return playerRank;
     331             : }
     332             : 
     333          28 : void setPlayerRank(uint8_t newRank) {
     334          28 :     playerRank = newRank;
     335          28 : }
     336             : 
     337          18 : void moveBy(uint8_t direction) {
     338             :     uint8_t c;
     339          18 :     uint8_t previousLocation = playerLocation;
     340             : 
     341          18 :     struct Room *room = &rooms[playerLocation];
     342          25 :     if (direction <= 5 && room->connections[direction] != 0) {
     343          14 :         struct Item *coupling = getItemNamed("magnetic-coupling");
     344          14 :         room = &rooms[playerLocation];
     345             : 
     346          14 :         if (rooms[room->connections[direction]].rankRequired > playerRank) {
     347           3 :             defaultLogger("Insufficient rank to enter room");
     348           3 :             return;
     349             :         }
     350             : 
     351          11 :         if (room == getRoomByName("hangar") && coupling->active && direction == 0) {
     352           0 :             defaultLogger("The magnetic coupling is\nengaged. The door won't open.");
     353           0 :             return;
     354             :         }
     355             : 
     356          11 :         playerLocation = room->connections[direction];
     357          11 :         room = &rooms[playerLocation];
     358             : 
     359          11 :         if (direction < 4) {
     360          49 :             for (c = 0; c < 6; ++c) {
     361          42 :                 if (room->connections[c] == previousLocation) {
     362           7 :                     direction = c;
     363             :                 }
     364             :             }
     365             :         } else {
     366           4 :             return;
     367             :         }
     368             : 
     369           7 :         switch (direction) {
     370           5 :             case 2:
     371           5 :                 playerPosition.x = rooms[playerLocation].sizeX / 2;
     372           5 :                 playerPosition.y = rooms[playerLocation].sizeY - 1;
     373           5 :                 break;
     374             : 
     375           1 :             case 3:
     376           1 :                 playerPosition.x = 0;
     377           1 :                 playerPosition.y = rooms[playerLocation].sizeY / 2;
     378           1 :                 break;
     379             : 
     380           0 :             case 1:
     381           0 :                 playerPosition.x = rooms[playerLocation].sizeX - 1;
     382           0 :                 playerPosition.y = rooms[playerLocation].sizeY / 2;
     383           0 :                 break;
     384           1 :             case 0:
     385             :             default:
     386           1 :                 playerPosition.x = rooms[playerLocation].sizeX / 2;
     387           1 :                 playerPosition.y = 0;
     388           1 :                 break;
     389             :         }
     390             : #ifdef CLI_BUILD
     391           4 :         } else if ( errorHandlerCallback) {
     392           2 :             errorHandlerCallback("Please specify a valid direction");
     393             : #endif
     394             :     }
     395             : }
     396             : 
     397          24 : void pickObjectByName(const char *objName) {
     398          24 :     struct Room *room = &rooms[playerLocation];
     399          24 :     struct ObjectNode *itemToPick = room->itemsPresent->next;
     400             : 
     401          84 :     while (itemToPick != NULL) {
     402          83 :         if (!strcmp(getItem(itemToPick->item)->name, objName)) {
     403             : #ifdef MOVE_TO_OBJECT_POSITION_WHEN_PICKING
     404          23 :             playerPosition = getItem(itemToPick->item)->position;
     405             : #endif
     406          23 :             pickObject(getItem(itemToPick->item));
     407          23 :             return;
     408             :         }
     409          60 :         itemToPick = itemToPick->next;
     410             :     }
     411             : }
     412             : 
     413          12 : void dropObjectByName(const char *objName) {
     414          12 :     struct ObjectNode *itemToPick = collectedObject->next;
     415             : 
     416             : 
     417          37 :     while (itemToPick != NULL) {
     418          36 :         if (!strcmp(getItem(itemToPick->item)->name, objName)) {
     419          11 :             dropObjectToRoom(playerLocation, getItem(itemToPick->item));
     420          11 :             return;
     421             :         }
     422          25 :         itemToPick = itemToPick->next;
     423             :     }
     424             : 
     425             : #ifdef CLI_BUILD
     426           1 :     errorHandlerCallback("Unable to locate object");
     427             : #endif
     428             : 
     429             : }
     430             : 
     431          68 : uint8_t hasItemInRoom(const char *roomName, const char *itemName) {
     432             :     struct ObjectNode *itemToPick;
     433             : 
     434             : #ifdef CLI_BUILD
     435             :     struct Room* room;
     436             : 
     437          68 :     if (roomName == NULL || itemName == NULL || strlen(roomName) == 0 || strlen(itemName) == 0) {
     438           4 :         defaultLogger("Either the object name or the room name are null. Check your stuff");
     439           4 :         return 0;
     440             :     }
     441             : #endif
     442             : 
     443             : #ifdef CLI_BUILD
     444          64 :     room = getRoomByName(roomName);
     445             : 
     446          64 :     if (room != NULL) {
     447          63 :         itemToPick = room->itemsPresent->next;
     448             :     } else {
     449           1 :         errorHandlerCallback("Invalid room name");
     450           1 :         return 0;
     451             :     }
     452             : #else
     453             :     itemToPick = getRoomByName(roomName)->itemsPresent->next;
     454             : #endif
     455             : 
     456         199 :     while (itemToPick != NULL) {
     457         167 :         struct Item *pick = getItem(itemToPick->item);
     458         167 :         if (!strcmp(pick->name, itemName)) {
     459          31 :             return 1;
     460             :         }
     461         136 :         itemToPick = itemToPick->next;
     462             :     }
     463             : 
     464          32 :     return 0;
     465             : }
     466             : 
     467          91 : uint8_t playerHasObject(const char *itemName) {
     468          91 :     struct ObjectNode *itemToPick = collectedObject->next;
     469             : 
     470         322 :     while (itemToPick != NULL) {
     471         255 :         if (!strcmp(getItem(itemToPick->item)->name, itemName)) {
     472          24 :             return 1;
     473             :         }
     474         231 :         itemToPick = itemToPick->next;
     475             :     }
     476          67 :     return 0;
     477             : }
     478             : 
     479             : 
     480          11 : uint8_t isPlayerAtRoom(const char *roomName) {
     481          11 :     struct Room *room = &rooms[playerLocation];
     482          11 :     const char *name = room->name;
     483          11 :     uint8_t returnValue = !strcmp(name, roomName);
     484          11 :     return returnValue;
     485             : }
     486             : 
     487           0 : const char *getRoomDescription(void) {
     488           0 :     struct Room *room = &rooms[playerLocation];
     489           0 :     return room->name;
     490             : }
     491             : 
     492          53 : struct Room *getRoom(uint8_t index) {
     493          53 :     return &rooms[index];
     494             : }
     495             : 
     496        1710 : struct Item *getItem(uint8_t index) {
     497        1710 :     return &item[index];
     498             : }
     499             : 
     500          51 : uint8_t getPlayerRoom(void) {
     501          51 :     return playerLocation;
     502             : }
     503             : 
     504          23 : void useObjectNamed(const char *operand) {
     505          23 :     struct ObjectNode *itemToPick = getPlayerItems();
     506             : 
     507          69 :     while (itemToPick != NULL) {
     508          49 :         struct Item *_item = getItem(itemToPick->item);
     509          49 :         if (!strcmp(_item->name, operand)) {
     510           3 :             if (_item->useCallback != NULL) {
     511           3 :                 _item->useCallback(_item);
     512             :             }
     513           3 :             return;
     514             :         }
     515          46 :         itemToPick = itemToPick->next;
     516             :     }
     517             : 
     518          20 :     itemToPick = getRoom(playerLocation)->itemsPresent->next;
     519             : 
     520          36 :     while (itemToPick != NULL) {
     521          33 :         struct Item *_item = getItem(itemToPick->item);
     522          33 :         if (!strcmp(_item->name, operand)) {
     523          17 :             if (_item->useCallback != NULL) {
     524          17 :                 _item->useCallback(_item);
     525             :             }
     526          17 :             return;
     527             :         }
     528          16 :         itemToPick = itemToPick->next;
     529             :     }
     530             : }
     531             : 
     532             : #ifdef CLI_BUILD
     533           4 : void walkTo(const char *operands) {
     534             :     struct WorldPosition pos;
     535             :     char *xStr;
     536             :     char *yStr;
     537             :     int8_t x;
     538             :     int8_t y;
     539             : 
     540           4 :     xStr = (char*)operands;
     541           4 :     yStr = strtok(NULL, "\n ");
     542           4 :     x = atoi(xStr);
     543           4 :     y = atoi(yStr);
     544           4 :     pos.x = x;
     545           4 :     pos.y = y;
     546           4 :     setPlayerPosition(&pos);
     547           4 : }
     548             : 
     549             : #ifdef INCLUDE_ITEM_DESCRIPTIONS
     550             : void infoAboutItemNamed(const char *itemName) {
     551             : 
     552             :     struct ObjectNode *object1 = collectedObject->next;
     553             :     struct Room *room = &rooms[playerLocation];
     554             :     struct ObjectNode *object2 = room->itemsPresent->next;
     555             : 
     556             :     if (itemName == NULL || strlen(itemName) == 0) {
     557             : #ifdef INCLUDE_ROOM_DESCRIPTIONS
     558             :         defaultLogger(room->info);
     559             : #endif
     560             :         return;
     561             :     }
     562             : 
     563             :     while (object1 != NULL) {
     564             :         struct Item* item = getItem(object1->item);
     565             :         assert(item->name != NULL);
     566             : 
     567             :         if (!strcmp(item->name, itemName)) {
     568             :             defaultLogger(item->info);
     569             :             return;
     570             :         }
     571             :         object1 = object1->next;
     572             :     }
     573             : 
     574             :     while (object2 != NULL) {
     575             :         struct Item* item = getItem(object2->item);
     576             :         assert(item->name != NULL);
     577             : 
     578             :         if (!strcmp(item->name, itemName)) {
     579             :             defaultLogger(item->info);
     580             :             return;
     581             :         }
     582             :         object2 = object2->next;
     583             :     }
     584             : #ifdef CLI_BUILD
     585             :     defaultLogger("No such item could be found");
     586             : #endif
     587             : }
     588             : #endif
     589             : 
     590           2 : void useObjectsTogether(const char *operands) {
     591             : 
     592           2 :     struct ObjectNode *object1 = collectedObject->next;
     593           2 :     struct Room *room = &rooms[playerLocation];
     594           2 :     struct ObjectNode *object2 = room->itemsPresent->next;
     595             : 
     596           2 :     char *operand1 = (char*)operands;
     597           2 :     char *operand2 = strtok(NULL, "\n ");
     598             : 
     599           2 :     if (!playerHasObject(operand1)) {
     600             : #ifdef CLI_BUILD
     601           0 :         defaultLogger("You do not have this object");
     602             : #endif
     603           0 :         return;
     604             :     }
     605             : 
     606           2 :     if (!hasItemInRoom(getRoom(playerLocation)->name, operand2)) {
     607             : #ifdef CLI_BUILD
     608           0 :         defaultLogger("That object is not present in the room");
     609             : #endif
     610           0 :         return;
     611             :     }
     612             : 
     613           6 :     while (object1 != NULL) {
     614           6 :         struct Item* _item = getItem(object1->item);
     615           6 :         assert(_item->name != NULL);
     616             : 
     617           6 :         if (!strcmp(_item->name, operand1)) {
     618           2 :             goto got_first_object;
     619             :         }
     620           4 :         object1 = object1->next;
     621             :     }
     622             : 
     623           0 :     got_first_object:
     624           5 :     while (object2 != NULL) {
     625           5 :         struct Item* _item = getItem(object2->item);
     626           5 :         assert(_item->name != NULL);
     627             : 
     628           5 :         if (!strcmp(_item->name, operand2)) {
     629           2 :             goto got_second_object;
     630             :         }
     631           3 :         object2 = object2->next;
     632             :     }
     633             : 
     634           0 :     got_second_object:
     635           2 :     if (object1 != NULL){
     636           2 :         struct Item* _item = getItem(object1->item);
     637             : 
     638           2 :         if (_item != NULL && _item->useWithCallback != NULL && object2 != NULL) {
     639           2 :             _item->useWithCallback(_item, getItem(object2->item));
     640             :         }
     641             :     }
     642             : }
     643             : #endif
     644             : 
     645           4 : void turnLeft(void) {
     646           4 :         uint8_t pDir = (uint8_t) playerDirection;
     647           4 :         pDir--;
     648             :     
     649           4 :     pDir = pDir & 3;
     650           4 :         playerDirection = (enum EDirection)pDir;
     651           4 : }
     652             : 
     653           4 : void turnRight(void) {
     654           4 :         uint8_t pDir = (uint8_t) playerDirection;
     655           4 :     pDir++;
     656             : 
     657           4 :     pDir = pDir & 3;
     658           4 :         playerDirection = (enum EDirection)pDir;
     659           4 : }
     660             : 
     661          18 : void setPlayerLocation(uint8_t location) {
     662          18 :     playerLocation = location;
     663          18 : }
     664             : 
     665          19 : void walkBy(uint8_t direction) {
     666             : 
     667          19 :     switch (direction) {
     668           5 :         case 1:
     669           5 :             switch (playerDirection) {
     670           1 :                 case 1:
     671           1 :                     playerPosition.y += WALK_STEP;
     672           1 :                     break;
     673           1 :                 case 2:
     674           1 :                     playerPosition.x -= WALK_STEP;
     675           1 :                     break;
     676           1 :                 case 3:
     677           1 :                     playerPosition.y -= WALK_STEP;
     678           1 :                     break;
     679           2 :                 case 0:
     680             :                 default:
     681           2 :                     playerPosition.x += WALK_STEP;
     682           2 :                     break;
     683             :             }
     684           5 :             break;
     685           5 :         case 2:
     686           5 :             switch (playerDirection) {
     687           1 :                 case 1:
     688           1 :                     playerPosition.x -= WALK_STEP;
     689           1 :                     break;
     690           1 :                 case 2:
     691           1 :                     playerPosition.y -= WALK_STEP;
     692           1 :                     break;
     693           1 :                 case 3:
     694           1 :                     playerPosition.x += WALK_STEP;
     695           1 :                     break;
     696           2 :                 case 0:
     697             :                 default:
     698           2 :                     playerPosition.y += WALK_STEP;
     699           2 :                     break;
     700             :             }
     701           5 :             break;
     702           5 :         case 3:
     703           5 :             switch (playerDirection) {
     704           1 :                 case 1:
     705           1 :                     playerPosition.y -= WALK_STEP;
     706           1 :                     break;
     707           1 :                 case 2:
     708           1 :                     playerPosition.x += WALK_STEP;
     709           1 :                     break;
     710           1 :                 case 3:
     711           1 :                     playerPosition.y += WALK_STEP;
     712           1 :                     break;
     713           2 :                 case 0:
     714             :                 default:
     715           2 :                     playerPosition.x -= WALK_STEP;
     716           2 :                     break;
     717             :             }
     718           5 :             break;
     719           4 :         case 0:
     720             :         default:
     721           4 :             switch (playerDirection) {
     722           1 :                 case 1:
     723           1 :                     playerPosition.x += WALK_STEP;
     724           1 :                     break;
     725           1 :                 case 2:
     726           1 :                     playerPosition.y += WALK_STEP;
     727           1 :                     break;
     728           1 :                 case 3:
     729           1 :                     playerPosition.x -= WALK_STEP;
     730           1 :                     break;
     731           1 :                 case 0:
     732             :                 default:
     733           1 :                     playerPosition.y -= WALK_STEP;
     734           1 :                     break;
     735             :             }
     736           4 :             break;
     737             :     }
     738             : 
     739             : #ifdef CLI_BUILD
     740          19 :     if (playerPosition.x < 0) {
     741           1 :       playerPosition.x = 0;
     742             :     }
     743             : 
     744          19 :     if (playerPosition.y < 0) {
     745           0 :         playerPosition.y = 0;
     746             :     }
     747             : 
     748             : 
     749          19 :     if (playerPosition.x >= rooms[playerLocation].sizeX) {
     750           1 :         playerPosition.x = rooms[playerLocation].sizeX - 1;
     751             :     }
     752             : 
     753          19 :     if (playerPosition.y >= rooms[playerLocation].sizeY) {
     754           1 :         playerPosition.y = rooms[playerLocation].sizeY - 1;
     755             :     }
     756             : #endif
     757          19 : }
     758             : 
     759          10 : enum EDirection getPlayerDirection(void) {
     760          10 :     return playerDirection;
     761             : }
     762             : 
     763        1565 : void addToRoom(const char *roomName, struct Item *itemName) {
     764             :     uint8_t r;
     765             : 
     766             : #ifdef CLI_BUILD
     767        1565 :     if (roomName == NULL || itemName == NULL || strlen(roomName) == 0) {
     768           3 :         defaultLogger("Either the object name or the room name are null. Check your stuff");
     769           3 :         return;
     770             :     }
     771             : #endif
     772             : 
     773       18532 :     for (r = 1; r < TOTAL_ROOMS; ++r) {
     774       18531 :         const char *desc = rooms[r].name;
     775             : 
     776       18531 :         if (desc != NULL && !strcmp(desc, roomName)) {
     777        1561 :             addObjectToRoom(r, itemName);
     778        1561 :             return;
     779             :         }
     780             :     }
     781             : 
     782             : #ifdef CLI_BUILD
     783           1 :     defaultLogger("It was not possible to determine the room to add object");
     784             : #endif
     785             : }
     786             : 
     787          38 : void setLoggerDelegate(LogDelegate newDelegate) {
     788          38 :     defaultLogger = newDelegate;
     789          38 : }
     790             : 
     791             : 
     792           1 : void setPlayerDirection(enum EDirection direction) {
     793           1 :     playerDirection = direction;
     794           1 : }
     795             : 
     796           7 : void setGameStatus(enum EGameStates newStatus) {
     797           7 :     gameStatus = newStatus;
     798           7 : }
     799             : 
     800          53 : void initCore(void) {
     801          53 :     defaultLogger = writeToLog;
     802             :     /* prepare for a single player in the game */
     803          53 :     memFill(&playerPosition, 0, sizeof(struct WorldPosition));
     804          53 :     setErrorHandlerCallback(NULL);
     805             : 
     806          53 :     collectedObject = &collectedObjectHead;
     807          53 :     memFill(collectedObject, 0, sizeof(struct ObjectNode));
     808          53 :     playerLocation = 1;
     809          53 :     itemsCount = 0;
     810          53 :     roomCount = 1; /* there's an implicit dummy first */
     811          53 :     playerRank = 0;
     812          53 :     gameStatus = kNormalGameplay;
     813          53 :     playerDirection = kNorth;
     814          53 :     playerPosition.x = 15;
     815          53 :     playerPosition.y = 15;
     816             : 
     817          53 :     memFill(&rooms, 0, TOTAL_ROOMS * sizeof(struct Room));
     818          53 :     memFill(&item, 0, TOTAL_ITEMS * sizeof(struct Item));
     819          53 : }
     820             : 
     821             : 
     822             : 
     823             : 

Generated by: LCOV version 1.14